Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/xpath/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android中希伯来语元音点的对齐_Android_Text_Hebrew - Fatal编程技术网

Android中希伯来语元音点的对齐

Android中希伯来语元音点的对齐,android,text,hebrew,Android,Text,Hebrew,我想使用Canvas.drawText界面显示带有元音点(nikkud)的希伯来文文本。元音点出现错位,如下图所示,使用摩托罗拉Defy+设备拍摄: hiriq在resh和yod之间,holam在vav和nun之间。 我已经将rtl代码(\u200F)添加到字符串的两端,没有乐趣。 我知道有一些应用程序已经解决了这个问题,比如Smart Siddur。基于文本的应用程序和基于图形的应用程序之间有区别吗?我认为在这两种情况下,相同的引擎呈现文本。我想我可以拆分字符串并分别放置元音,但这似乎非常痛

我想使用Canvas.drawText界面显示带有元音点(nikkud)的希伯来文文本。元音点出现错位,如下图所示,使用摩托罗拉Defy+设备拍摄:

hiriq在resh和yod之间,holam在vav和nun之间。 我已经将rtl代码(\u200F)添加到字符串的两端,没有乐趣。 我知道有一些应用程序已经解决了这个问题,比如Smart Siddur。基于文本的应用程序和基于图形的应用程序之间有区别吗?我认为在这两种情况下,相同的引擎呈现文本。我想我可以拆分字符串并分别放置元音,但这似乎非常痛苦,而且无法扩展。

TIA提供任何线索。

这可能是您使用的字体有问题,因为您也可能在台式计算机上重现相同的问题。尽管安卓系统本身现在有希伯来文的标志符号,但供应商之间有很大的差异,所以即使它在一台设备上运行良好,也不能在其他所有设备上运行良好


我的建议是通过提供自己的字体来解决这个问题。例如,您可以使用来自的字体,这些字体是免费的,并且大多数已知的字体足以支持希伯来语元音点

这可能是您使用的字体的问题,因为您也可能在桌面计算机上重现相同的问题。尽管安卓系统本身现在有希伯来文的标志符号,但供应商之间有很大的差异,所以即使它在一台设备上运行良好,也不能在其他所有设备上运行良好


我的建议是通过提供自己的字体来解决这个问题。例如,您可以使用来自的字体,这些字体是免费的,并且大多数已知的字体足以支持希伯来语元音点

好吧,下面的方法很有效。我仍然不明白为什么我必须实施它,但这确实有效

 package com.lomda.ong2;

import java.util.HashMap;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Paint.FontMetricsInt;
import android.graphics.Typeface;
import android.graphics.Paint.Align;
import android.graphics.Paint.FontMetrics;
import android.graphics.Point;
import android.graphics.Rect;
import android.util.Log;

// render Hebrew strings with diacritic marks
// 
public class HebRender {

Paint paint;
HashMap<String, Integer> spaces;
String charString;
String prevChar = "";
final String TAG = "HebRender";

public HebRender(Context svContext){
    paint = new Paint(); 
    Typeface t =  Typeface.createFromAsset(svContext.getAssets(),"fonts/SimpleCLM-Bold.ttf");
    //Typeface t =  Typeface.createFromAsset(svContext.getAssets(),"fonts/gisha.ttf");
    paint.setTypeface(t);
    paint.setStyle(Paint.Style.FILL); 
    paint.setTextSize(48); 
    paint.setAntiAlias(true); 
    paint.setTypeface(Typeface.DEFAULT_BOLD); 
    paint.setTextAlign(Align.CENTER);
}

public void drawText(   Canvas canvas, String word, Point locate, int color) {
    Rect bounds = new Rect();
    Rect prevBounds = new Rect(0,0,0,0);
    paint.getTextBounds(word, 0, word.length(), bounds);
    paint.setColor(color);
    int wordWidth = bounds.width();
    // move to right edge (parameter is center)
    locate.x += wordWidth/2;
    // initialize bounds of individual characters
    bounds = new Rect(0,0,0,0);
    // for each character
    for (int i = 0; i < word.length(); i++) {
        // locate and write letter
        char c = word.charAt(i);
        charString = String.valueOf(c); 
        if (c >= 1488 && c <=1514) {// is in consonant range
            paint.getTextBounds(charString, 0, charString.length(), bounds); // get current char dimensions
            if (!prevChar.equals("")) {
                int moveOver = bounds.width()/2 + prevBounds.width()/2 + (int) paint.getTextSize()/10;
                locate.x -= moveOver;
            }
            Log.d(TAG, String.format("Char: %s, Prev char width: %d, char width: %d", charString, prevBounds.width(), bounds.width()));
            canvas.drawText(charString, locate.x, locate.y, paint);
            prevChar = charString;
            prevBounds.set(bounds); // save previous dimensions
        } else {// for each diacritic locate and write
            canvas.drawText(charString, locate.x + getOffset(c, bounds.width()), locate.y, paint);
        }

    }
}

// some diacritic marks need to be moved 
private int getOffset(char c, int charWidth) {
    int offset = 0;
    switch (c){
    case 0x05C1:  // shin dot
        offset = charWidth/2;
        break;
    case 0x05C2:  // sin dot
        offset = -charWidth/2;
        break;
    case 0x05BC:  // dagesh
        offset = findDagesh(c, charWidth);
        break;
    case 0x05B9: // holam
        offset = -(3*charWidth/5);
        break;
    }
    return offset;
}

// move dagesh around for certain characters
private int findDagesh(char c, int charWidth) {
    int offset = 0;
    if (prevChar.equals("ג")) {
        offset = Math.min(2, -charWidth/3);
    } else if (prevChar.equals("ו") ||prevChar.equals("ז") || prevChar.equals("י")){
        offset = Math.min(7, -7*charWidth/10);
    } else if (prevChar.equals("ע") || prevChar.equals("ש") ) {
        offset = Math.max(1, charWidth/3);
    } else if (prevChar.equals("פ")){
        offset = Math.max(2, charWidth/3);
    }
    return offset;
}
package com.lomda.ong2;
导入java.util.HashMap;
导入android.content.Context;
导入android.graphics.Canvas;
导入android.graphics.Color;
导入android.graphics.Paint;
导入android.graphics.Paint.FontMetricsInt;
导入android.graphics.Typeface;
导入android.graphics.Paint.Align;
导入android.graphics.Paint.FontMetrics;
导入android.graphics.Point;
导入android.graphics.Rect;
导入android.util.Log;
//用变音符号呈现希伯来语字符串
// 
公共类希布伦德{
油漆;
HashMap空间;
字符串字符串;
字符串prevChar=“”;
最后一个字符串标记=“HebRender”;
公共HebRender(上下文svContext){
油漆=新油漆();
Typeface t=Typeface.createFromAsset(svContext.getAssets(),“font/simplecm Bold.ttf”);
//Typeface t=Typeface.createFromAsset(svContext.getAssets(),“fonts/gisha.ttf”);
油漆。设置字体(t);
绘制.设置样式(绘制.样式.填充);
油漆.尺寸(48);
paint.setAntiAlias(真);
paint.setTypeface(Typeface.DEFAULT_BOLD);
paint.setTextAlign(Align.CENTER);
}
公共void drawText(画布、字符串字、点定位、int颜色){
Rect bounds=new Rect();
Rect prevBounds=新的Rect(0,0,0,0);
paint.getTextBounds(word,0,word.length(),bounds);
油漆。设置颜色(颜色);
int wordWidth=bounds.width();
//移动到右边缘(参数为“中心”)
locate.x+=wordWidth/2;
//初始化单个字符的边界
边界=新的矩形(0,0,0,0);
//对于每个字符
for(int i=0;i如果(c>=1488&&c那么,下面的方法行得通。我仍然不明白为什么要实现它,但这确实行得通

 package com.lomda.ong2;

import java.util.HashMap;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Paint.FontMetricsInt;
import android.graphics.Typeface;
import android.graphics.Paint.Align;
import android.graphics.Paint.FontMetrics;
import android.graphics.Point;
import android.graphics.Rect;
import android.util.Log;

// render Hebrew strings with diacritic marks
// 
public class HebRender {

Paint paint;
HashMap<String, Integer> spaces;
String charString;
String prevChar = "";
final String TAG = "HebRender";

public HebRender(Context svContext){
    paint = new Paint(); 
    Typeface t =  Typeface.createFromAsset(svContext.getAssets(),"fonts/SimpleCLM-Bold.ttf");
    //Typeface t =  Typeface.createFromAsset(svContext.getAssets(),"fonts/gisha.ttf");
    paint.setTypeface(t);
    paint.setStyle(Paint.Style.FILL); 
    paint.setTextSize(48); 
    paint.setAntiAlias(true); 
    paint.setTypeface(Typeface.DEFAULT_BOLD); 
    paint.setTextAlign(Align.CENTER);
}

public void drawText(   Canvas canvas, String word, Point locate, int color) {
    Rect bounds = new Rect();
    Rect prevBounds = new Rect(0,0,0,0);
    paint.getTextBounds(word, 0, word.length(), bounds);
    paint.setColor(color);
    int wordWidth = bounds.width();
    // move to right edge (parameter is center)
    locate.x += wordWidth/2;
    // initialize bounds of individual characters
    bounds = new Rect(0,0,0,0);
    // for each character
    for (int i = 0; i < word.length(); i++) {
        // locate and write letter
        char c = word.charAt(i);
        charString = String.valueOf(c); 
        if (c >= 1488 && c <=1514) {// is in consonant range
            paint.getTextBounds(charString, 0, charString.length(), bounds); // get current char dimensions
            if (!prevChar.equals("")) {
                int moveOver = bounds.width()/2 + prevBounds.width()/2 + (int) paint.getTextSize()/10;
                locate.x -= moveOver;
            }
            Log.d(TAG, String.format("Char: %s, Prev char width: %d, char width: %d", charString, prevBounds.width(), bounds.width()));
            canvas.drawText(charString, locate.x, locate.y, paint);
            prevChar = charString;
            prevBounds.set(bounds); // save previous dimensions
        } else {// for each diacritic locate and write
            canvas.drawText(charString, locate.x + getOffset(c, bounds.width()), locate.y, paint);
        }

    }
}

// some diacritic marks need to be moved 
private int getOffset(char c, int charWidth) {
    int offset = 0;
    switch (c){
    case 0x05C1:  // shin dot
        offset = charWidth/2;
        break;
    case 0x05C2:  // sin dot
        offset = -charWidth/2;
        break;
    case 0x05BC:  // dagesh
        offset = findDagesh(c, charWidth);
        break;
    case 0x05B9: // holam
        offset = -(3*charWidth/5);
        break;
    }
    return offset;
}

// move dagesh around for certain characters
private int findDagesh(char c, int charWidth) {
    int offset = 0;
    if (prevChar.equals("ג")) {
        offset = Math.min(2, -charWidth/3);
    } else if (prevChar.equals("ו") ||prevChar.equals("ז") || prevChar.equals("י")){
        offset = Math.min(7, -7*charWidth/10);
    } else if (prevChar.equals("ע") || prevChar.equals("ש") ) {
        offset = Math.max(1, charWidth/3);
    } else if (prevChar.equals("פ")){
        offset = Math.max(2, charWidth/3);
    }
    return offset;
}
package com.lomda.ong2;
导入java.util.HashMap;
导入android.content.Context;
导入android.graphics.Canvas;
导入android.graphics.Color;
导入android.graphics.Paint;
导入android.graphics.Paint.FontMetricsInt;
导入android.graphics.Typeface;
导入android.graphics.Paint.Align;
导入android.graphics.Paint.FontMetrics;
导入android.graphics.Point;
导入android.graphics.Rect;
导入android.util.Log;
//用变音符号呈现希伯来语字符串
// 
公共类希布伦德{
油漆;
HashMap空间;
字符串字符串;
字符串prevChar=“”;
最后一个字符串标记=“HebRender”;
公共HebRender(上下文svContext){
油漆=新油漆();
Typeface t=Typeface.createFromAsset(svContext.getAssets(),“font/simplecm Bold.ttf”);
//Typeface t=Typeface.createFromAsset(svContext.getAssets(),“fonts/gisha.ttf”);
油漆。设置字体(t);
绘制.设置样式(绘制.样式.填充);
油漆.尺寸(48);
paint.setAntiAlias(真);
paint.setTypeface(Typeface.DEFAULT_BOLD);
paint.setTextAlign(Align.CENTER);
}
公共void drawText(画布、字符串字、点定位、int颜色){
Rect bounds=new Rect();
Rect prevBounds=新的Rect(0,0,0,0);
paint.getTextBounds(word,0,word.length(),bounds);
油漆。设置颜色(颜色);
int wordWidth=bounds.width();
//移动到右边缘(参数为“中心”)
locate.x+=wordWidth/2;
//初始化单个字符的边界
边界=新的矩形(0,0,0,0);
//对于每个字符
for(int i=0;i如果(c>=1488&&c我尝试了来自Culmus的Gisha字体和简单字体。两者都没有乐趣。我尝试了在字符串两端添加\u200F的所有可能组合。组合和单独使用时,我尝试了paint.setTextAlign(Align.RIGHT/Align.LEFT/Align.Center)。这些参数似乎都没有任何效果。
此时,我正在尝试实现一个手动解决方案,分别迭代每个代码点。我不敢相信这还没有解决。我尝试了Gisha字体和Culmus的简单字体。两者都没有乐趣。我尝试了所有可能的方法