2016-03-28 16 views
3

Özel bir yuvarlak metin kutusuna sahibim ve yuvarlanmış parçalara metin yazmak istemiyorum, bu nedenle dize başlangıcından ne kadar karakterin belirtileceğini bilmek istiyorum. Bir dizeyi ölçmek için TextRenderer.MeasureText'u biliyorum, ancak yalnızca bir dizenin genişliğini verir, ters yönde çalışmaz. Bunu nasıl yapabilirim?Bir genişlik değerine göre dize parçası nasıl alınır?

Bunu yapabilirim, ancak bazen çok zaman alabilir.

string resultText = string.Empty; 

    for (int i = 0; i < Text.Length; i++) 
    { 
     resultString = Text.Substring(0, i); 
     if (TextRenderer.MeasureText(resultText, Font).Width <= textWidth) 
      break; 
    } 
+1

Bu ne tür bir uygulama? düzgün etiketleme kullanın –

+0

Bu bir Windows Form Uygulama –

+0

Bir sabit genişlikli yazı tipi kullanmıyorsanız, tüm karakterler farklı genişliklere sahip olacak, bu nedenle böyle bir şey yapmanız gerekecek. – TaW

cevap

0

Dönüsüz daha iyi bir çözüm buldum. Bu yöntemde, mevcut genişlik ve hedef genişlik arasındaki bir oranı hesaplıyoruz. Ve eğer bu oran, dizenin şu anki uzunluğu ile çarpılırsa, iyi bir alt tabaka noktası elde ederiz.

string GetSubStringToWidth(string orgText, int width, Font font) 
    { 
     int orgWidth = TextRenderer.MeasureText(orgText, font).Width; 

     float ratio = (float)width/orgWidth; 

     int length = (int)(orgText.Length * ratio); 

     if (length >= orgText.Length) return orgText; 
     else if (length <= 0) return ""; 
     else 
     { 
      //May be more sensitive if we go right or left one unit because of letter unequalities 
      int mid = Math.Abs(width - TextRenderer.MeasureText(orgText.Substring(0, length), font).Width); 
      int right = Math.Abs(width - TextRenderer.MeasureText(orgText.Substring(0, length + 1), font).Width); 
      int left = Math.Abs(width - TextRenderer.MeasureText(orgText.Substring(0, length - 1), font).Width); 

      int i = Math.Min(Math.Min(mid, right), left); 
      int point = 0; 

      if (i == mid) 
       point = length; 
      else if (i == right) 
       point = length + 1; 
      else 
       point = length - 1; 

      return orgText.Substring(0, point); 
     } 
    } 
+0

Bu, her tür içerikte iyi çalışacağından kuşkuluyum. Ayrıca zamanlamayla ilgili endişelerinizin gerçek bir sebebi olduğundan şüphe duyuyorum. 'Erken optimizasyon tüm kötülüklerin köküdür'. Ve tabiki metin kesmek genellikle, metin, kesip çıkarır .. – TaW

+0

Sadece kodumda test ettim. Metin kutusunun ortasını yazdı ve istediğim buydu. Tüm içerik üzerinde iyi çalışacağından emin değilim, ancak daha iyi. –

İlgili konular