Reorder English text?

G

Guest

Hi,

Below is a calss with function I gathered from a news group that uses
GetCharacterPlacement API to reorder text.
I have mixed text Hebrew/English and the function reorders the Hebrew text.

I would like to reorder the English text instead the Hebrew text.

How can I do that please?

Regards,
Asaf
--------------------------------------------------------------------------------------------

using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Windows.Forms;

namespace GetCharacterPlacement
{
class FlipHebrew
{
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
public struct GpcResults // Win32: GCP_RESULTS
{
public int StructSize;
[MarshalAs(UnmanagedType.LPTStr)]
public string OutString;
public IntPtr Order;
public IntPtr Dx;
public IntPtr CaretPos;
public IntPtr Class;
public IntPtr Glyphs;
public int GlyphCount;
public int MaxFit;
}


[Flags]
public enum GcpFlags // Win32: GCP_xxx flags, WinGDI.h
{
DBCS = 0x00000001,
ReOrder = 0x00000002,
UseKerning = 0x00000008,
GlyphShape = 0x00000010,
Ligate = 0x00000020,
Diacritic = 0x00000100,
Kashida = 0x00000400,
Error = 0x00008000,
Justify = 0x00010000,
FliGlyphs = 0x00040000,
ClassIn = 0x00080000,
MaxExtent = 0x00100000,
JustifyIn = 0x00200000,
DisplayZWG = 0x00400000,
SymSwapOff = 0x00800000,
NumericOverride = 0x01000000,
NeutralOverride = 0x02000000,
NumericsLatin = 0x04000000,
NumericsLocal = 0x08000000,


FliMask = 0x0000103B
}

[DllImport("gdi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern int GetCharacterPlacementW(IntPtr dev, string
text, int count, int max,
[In, Out] ref GpcResults results, GcpFlags flags);


[DllImport("gdi32.dll", ExactSpelling = true)]
public static extern GcpFlags GetFontLanguageInfo(IntPtr dev);


public string funcGetCharacterPlacement(string sTextToFlip)
{
Panel pnl = new Panel();
Graphics g = pnl.CreateGraphics();
IntPtr dev = g.GetHdc();

//string txt = "בדיקת עברית With English ועוד עברית";
string txt = sTextToFlip;
int len = txt.Length;

int[] order = new int[len];
int[] dx = new int[len];
int[] caret = new int[len];
byte[] clss = new byte[len];
short[] glys = new short[len];


GCHandle ordHnd = GCHandle.Alloc(order, GCHandleType.Pinned);
GCHandle dxHnd = GCHandle.Alloc(dx, GCHandleType.Pinned);
GCHandle carHnd = GCHandle.Alloc(caret, GCHandleType.Pinned);
GCHandle clsHnd = GCHandle.Alloc(clss, GCHandleType.Pinned);
GCHandle glyHnd = GCHandle.Alloc(glys, GCHandleType.Pinned);


try
{
GpcResults rs = new GpcResults();
rs.StructSize = Marshal.SizeOf(typeof(GpcResults));


rs.OutString = new String('\0', len + 2);
rs.Order = ordHnd.AddrOfPinnedObject();
rs.Dx = dxHnd.AddrOfPinnedObject();
rs.CaretPos = carHnd.AddrOfPinnedObject();
rs.Class = clsHnd.AddrOfPinnedObject();
rs.Glyphs = glyHnd.AddrOfPinnedObject();


rs.GlyphCount = len;
rs.MaxFit = 0;


GcpFlags flg = GcpFlags.FliMask & GetFontLanguageInfo(dev);
int r = GetCharacterPlacementW(dev, txt, len, 0, ref rs, flg);
if (r == 0) // 0:Error; OK e.g. 0x100085
{
int err = Marshal.GetLastWin32Error();
// todo: error handling
}

return rs.OutString;
}
finally
{
ordHnd.Free();
dxHnd.Free();
carHnd.Free();
clsHnd.Free();
glyHnd.Free();
// e.Graphics.ReleaseHdc(dev);
}

}
}
}
 
N

Nicholas Paldino [.NET/C# MVP]

Asaf,

First, there is no reason to pin the variables down before the call to
GetCharacterPlacement. The interop layer will handle the pinning of the
variables for you.

Also, you realize that the documentation for GetCharacterPlacement
states:

Although this function was once adequate for working with character strings,
a need to work with an increasing number of languages and scripts has
rendered it obsolete. It has been superseded by the functionality of the
Uniscribe module. For more information, see Uniscribe.

You might want to check those APIs for a more suitable function to call.

Hope this helps.

--
- Nicholas Paldino [.NET/C# MVP]
- (e-mail address removed)

Asaf said:
Hi,

Below is a calss with function I gathered from a news group that uses
GetCharacterPlacement API to reorder text.
I have mixed text Hebrew/English and the function reorders the Hebrew
text.

I would like to reorder the English text instead the Hebrew text.

How can I do that please?

Regards,
Asaf
--------------------------------------------------------------------------------------------

using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Windows.Forms;

namespace GetCharacterPlacement
{
class FlipHebrew
{
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
public struct GpcResults // Win32: GCP_RESULTS
{
public int StructSize;
[MarshalAs(UnmanagedType.LPTStr)]
public string OutString;
public IntPtr Order;
public IntPtr Dx;
public IntPtr CaretPos;
public IntPtr Class;
public IntPtr Glyphs;
public int GlyphCount;
public int MaxFit;
}


[Flags]
public enum GcpFlags // Win32: GCP_xxx flags, WinGDI.h
{
DBCS = 0x00000001,
ReOrder = 0x00000002,
UseKerning = 0x00000008,
GlyphShape = 0x00000010,
Ligate = 0x00000020,
Diacritic = 0x00000100,
Kashida = 0x00000400,
Error = 0x00008000,
Justify = 0x00010000,
FliGlyphs = 0x00040000,
ClassIn = 0x00080000,
MaxExtent = 0x00100000,
JustifyIn = 0x00200000,
DisplayZWG = 0x00400000,
SymSwapOff = 0x00800000,
NumericOverride = 0x01000000,
NeutralOverride = 0x02000000,
NumericsLatin = 0x04000000,
NumericsLocal = 0x08000000,


FliMask = 0x0000103B
}

[DllImport("gdi32.dll", CharSet = CharSet.Auto, SetLastError =
true)]
public static extern int GetCharacterPlacementW(IntPtr dev, string
text, int count, int max,
[In, Out] ref GpcResults results, GcpFlags flags);


[DllImport("gdi32.dll", ExactSpelling = true)]
public static extern GcpFlags GetFontLanguageInfo(IntPtr dev);


public string funcGetCharacterPlacement(string sTextToFlip)
{
Panel pnl = new Panel();
Graphics g = pnl.CreateGraphics();
IntPtr dev = g.GetHdc();

//string txt = "????? ????? With English ???? ?????";
string txt = sTextToFlip;
int len = txt.Length;

int[] order = new int[len];
int[] dx = new int[len];
int[] caret = new int[len];
byte[] clss = new byte[len];
short[] glys = new short[len];


GCHandle ordHnd = GCHandle.Alloc(order, GCHandleType.Pinned);
GCHandle dxHnd = GCHandle.Alloc(dx, GCHandleType.Pinned);
GCHandle carHnd = GCHandle.Alloc(caret, GCHandleType.Pinned);
GCHandle clsHnd = GCHandle.Alloc(clss, GCHandleType.Pinned);
GCHandle glyHnd = GCHandle.Alloc(glys, GCHandleType.Pinned);


try
{
GpcResults rs = new GpcResults();
rs.StructSize = Marshal.SizeOf(typeof(GpcResults));


rs.OutString = new String('\0', len + 2);
rs.Order = ordHnd.AddrOfPinnedObject();
rs.Dx = dxHnd.AddrOfPinnedObject();
rs.CaretPos = carHnd.AddrOfPinnedObject();
rs.Class = clsHnd.AddrOfPinnedObject();
rs.Glyphs = glyHnd.AddrOfPinnedObject();


rs.GlyphCount = len;
rs.MaxFit = 0;


GcpFlags flg = GcpFlags.FliMask & GetFontLanguageInfo(dev);
int r = GetCharacterPlacementW(dev, txt, len, 0, ref rs,
flg);
if (r == 0) // 0:Error; OK e.g. 0x100085
{
int err = Marshal.GetLastWin32Error();
// todo: error handling
}

return rs.OutString;
}
finally
{
ordHnd.Free();
dxHnd.Free();
carHnd.Free();
clsHnd.Free();
glyHnd.Free();
// e.Graphics.ReleaseHdc(dev);
}

}
}
}
 
T

TerryFei

Hi Asaf,
Based on the current situation, please help me to confirm some information
on your side: What exactly are you trying to get in the output? From my
experience, reordering Hebrew text follows the BIDI algorithm, there are no
rules for reordering English text.
This information will help us get closer to this issue, so I appreciate
your time in collecting it. Let me know the results at your earliest
convenience. If you have any questions or concerns, please let me know. I
am standing by to help you.

Best Regards,

Terry Fei [MSFT]
Microsoft Community Support
Get Secure! www.microsoft.com/security

--------------------
Thread-Topic: Reorder English text?
thread-index: AcYc3HXu25f1659dQkWEIFPxZsQ00A==
X-WBNR-Posting-Host: 213.8.95.84
From: "=?Utf-8?B?QXNhZg==?=" <[email protected]>
Subject: Reorder English text?
Date: Thu, 19 Jan 2006 01:41:02 -0800
Lines: 146
Message-ID: <[email protected]>
MIME-Version: 1.0
Content-Type: text/plain;
charset="Utf-8"
Content-Transfer-Encoding: 8bit
X-Newsreader: Microsoft CDO for Windows 2000
Content-Class: urn:content-classes:message
Importance: normal
Priority: normal
X-MimeOLE: Produced By Microsoft MimeOLE V6.00.3790.0
Newsgroups: microsoft.public.dotnet.languages.csharp
NNTP-Posting-Host: TK2MSFTNGXA03.phx.gbl 10.40.2.250
Path: TK2MSFTNGXA02.phx.gbl!TK2MSFTNGXA03.phx.gbl
Xref: TK2MSFTNGXA02.phx.gbl microsoft.public.dotnet.languages.csharp:379630
X-Tomcat-NG: microsoft.public.dotnet.languages.csharp

Hi,

Below is a calss with function I gathered from a news group that uses
GetCharacterPlacement API to reorder text.
I have mixed text Hebrew/English and the function reorders the Hebrew text.

I would like to reorder the English text instead the Hebrew text.

How can I do that please?

Regards,
Asaf ----------------------------------------------------------------------------
----------------

using System;
using System.Collections.Generic;
using System.Text;
using System.Drawing;
using System.Runtime.InteropServices;
using System.Windows.Forms;

namespace GetCharacterPlacement
{
class FlipHebrew
{
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
public struct GpcResults // Win32: GCP_RESULTS
{
public int StructSize;
[MarshalAs(UnmanagedType.LPTStr)]
public string OutString;
public IntPtr Order;
public IntPtr Dx;
public IntPtr CaretPos;
public IntPtr Class;
public IntPtr Glyphs;
public int GlyphCount;
public int MaxFit;
}


[Flags]
public enum GcpFlags // Win32: GCP_xxx flags, WinGDI.h
{
DBCS = 0x00000001,
ReOrder = 0x00000002,
UseKerning = 0x00000008,
GlyphShape = 0x00000010,
Ligate = 0x00000020,
Diacritic = 0x00000100,
Kashida = 0x00000400,
Error = 0x00008000,
Justify = 0x00010000,
FliGlyphs = 0x00040000,
ClassIn = 0x00080000,
MaxExtent = 0x00100000,
JustifyIn = 0x00200000,
DisplayZWG = 0x00400000,
SymSwapOff = 0x00800000,
NumericOverride = 0x01000000,
NeutralOverride = 0x02000000,
NumericsLatin = 0x04000000,
NumericsLocal = 0x08000000,


FliMask = 0x0000103B
}

[DllImport("gdi32.dll", CharSet = CharSet.Auto, SetLastError = true)]
public static extern int GetCharacterPlacementW(IntPtr dev, string
text, int count, int max,
[In, Out] ref GpcResults results, GcpFlags flags);


[DllImport("gdi32.dll", ExactSpelling = true)]
public static extern GcpFlags GetFontLanguageInfo(IntPtr dev);


public string funcGetCharacterPlacement(string sTextToFlip)
{
Panel pnl = new Panel();
Graphics g = pnl.CreateGraphics();
IntPtr dev = g.GetHdc();

//string txt = "בדיקת עברית With English ועוד ×¢× ‘רית";
string txt = sTextToFlip;
int len = txt.Length;

int[] order = new int[len];
int[] dx = new int[len];
int[] caret = new int[len];
byte[] clss = new byte[len];
short[] glys = new short[len];


GCHandle ordHnd = GCHandle.Alloc(order, GCHandleType.Pinned);
GCHandle dxHnd = GCHandle.Alloc(dx, GCHandleType.Pinned);
GCHandle carHnd = GCHandle.Alloc(caret, GCHandleType.Pinned);
GCHandle clsHnd = GCHandle.Alloc(clss, GCHandleType.Pinned);
GCHandle glyHnd = GCHandle.Alloc(glys, GCHandleType.Pinned);


try
{
GpcResults rs = new GpcResults();
rs.StructSize = Marshal.SizeOf(typeof(GpcResults));


rs.OutString = new String('\0', len + 2);
rs.Order = ordHnd.AddrOfPinnedObject();
rs.Dx = dxHnd.AddrOfPinnedObject();
rs.CaretPos = carHnd.AddrOfPinnedObject();
rs.Class = clsHnd.AddrOfPinnedObject();
rs.Glyphs = glyHnd.AddrOfPinnedObject();


rs.GlyphCount = len;
rs.MaxFit = 0;


GcpFlags flg = GcpFlags.FliMask & GetFontLanguageInfo(dev);
int r = GetCharacterPlacementW(dev, txt, len, 0, ref rs, flg);
if (r == 0) // 0:Error; OK e.g. 0x100085
{
int err = Marshal.GetLastWin32Error();
// todo: error handling
}

return rs.OutString;
}
finally
{
ordHnd.Free();
dxHnd.Free();
carHnd.Free();
clsHnd.Free();
glyHnd.Free();
// e.Graphics.ReleaseHdc(dev);
}

}
}
}
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top