⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 break.c

📁 Pango is a library for layout and rendering of text, with an emphasis on internationalization. Pang
💻 C
📖 第 1 页 / 共 4 页
字号:
/* Pango * break.c: * * Copyright (C) 1999 Red Hat Software * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License as published by the Free Software Foundation; either * version 2 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.	 See the GNU * Library General Public License for more details. * * You should have received a copy of the GNU Library General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */#include <config.h>#include "pango-break.h"#include "pango-modules.h"#include <string.h>#define PARAGRAPH_SEPARATOR 0x2029#define PARAGRAPH_SEPARATOR_STRING "\xE2\x80\xA9"/* See http://www.unicode.org/unicode/reports/tr14/ if you hope * to understand the line breaking code. */typedef enum{  BREAK_ALREADY_HANDLED,   /* didn't use the table */  BREAK_PROHIBITED, /* no break, even if spaces intervene */  BREAK_IF_SPACES,  /* "indirect break" (only if there are spaces) */  BREAK_ALLOWED     /* "direct break" (can always break here) */  /* TR 14 has one more break-opportunity class,   * "indirect break opportunity for combining marks following a space"   * but we handle that inline in the code.   */} BreakOpportunity;enum{  INDEX_OPEN_PUNCTUATION,  INDEX_CLOSE_PUNCTUATION,  INDEX_QUOTATION,  INDEX_NON_BREAKING_GLUE,  INDEX_NON_STARTER,  INDEX_EXCLAMATION,  INDEX_SYMBOL,  INDEX_INFIX_SEPARATOR,  INDEX_PREFIX,  INDEX_POSTFIX,  INDEX_NUMERIC,  INDEX_ALPHABETIC,  INDEX_IDEOGRAPHIC,  INDEX_INSEPARABLE,  INDEX_HYPHEN,  INDEX_AFTER,  INDEX_BEFORE,  INDEX_BEFORE_AND_AFTER,  INDEX_ZERO_WIDTH_SPACE,  INDEX_COMBINING_MARK,  INDEX_WORD_JOINER,  /* End of the table */  INDEX_END_OF_TABLE,  /* The following are not in the tables */  INDEX_MANDATORY,  INDEX_CARRIAGE_RETURN,  INDEX_LINE_FEED,  INDEX_SURROGATE,  INDEX_CONTINGENT,  INDEX_SPACE,  INDEX_COMPLEX_CONTEXT,  INDEX_AMBIGUOUS,  INDEX_UNKNOWN,  INDEX_NEXT_LINE,  INDEX_HANGUL_L_JAMO,  INDEX_HANGUL_V_JAMO,  INDEX_HANGUL_T_JAMO,  INDEX_HANGUL_LV_SYLLABLE,  INDEX_HANGUL_LVT_SYLLABLE,};static const BreakOpportunity row_OPEN_PUNCTUATION[INDEX_END_OF_TABLE] = {  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_CLOSE_PUNCTUATION[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_QUOTATION[INDEX_END_OF_TABLE] = {  BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_NON_BREAKING_GLUE[INDEX_END_OF_TABLE] = {  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_NON_STARTER[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_EXCLAMATION[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_SYMBOL[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_INFIX_SEPARATOR[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_PREFIX[INDEX_END_OF_TABLE] = {  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_POSTFIX[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_NUMERIC[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_ALPHABETIC[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_IDEOGRAPHIC[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_INSEPARABLE[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_HYPHEN[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_AFTER[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_BEFORE[INDEX_END_OF_TABLE] = {  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_BEFORE_AND_AFTER[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_ZERO_WIDTH_SPACE[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED, BREAK_ALLOWED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED};static const BreakOpportunity row_COMBINING_MARK[INDEX_END_OF_TABLE] = {  BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_ALLOWED, BREAK_ALLOWED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity row_WORD_JOINER[INDEX_END_OF_TABLE] = {  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_IF_SPACES,  BREAK_IF_SPACES, BREAK_IF_SPACES, BREAK_PROHIBITED, BREAK_PROHIBITED,  BREAK_PROHIBITED};static const BreakOpportunity *const line_break_rows[INDEX_END_OF_TABLE] = {  row_OPEN_PUNCTUATION, /* INDEX_OPEN_PUNCTUATION */  row_CLOSE_PUNCTUATION, /* INDEX_CLOSE_PUNCTUATION */  row_QUOTATION, /* INDEX_QUOTATION */  row_NON_BREAKING_GLUE, /* INDEX_NON_BREAKING_GLUE */  row_NON_STARTER, /* INDEX_NON_STARTER */  row_EXCLAMATION, /* INDEX_EXCLAMATION */  row_SYMBOL, /* INDEX_SYMBOL */  row_INFIX_SEPARATOR, /* INDEX_INFIX_SEPARATOR */  row_PREFIX, /* INDEX_PREFIX */  row_POSTFIX, /* INDEX_POSTFIX */  row_NUMERIC, /* INDEX_NUMERIC */  row_ALPHABETIC, /* INDEX_ALPHABETIC */  row_IDEOGRAPHIC, /* INDEX_IDEOGRAPHIC */  row_INSEPARABLE, /* INDEX_INSEPARABLE */  row_HYPHEN, /* INDEX_HYPHEN */  row_AFTER, /* INDEX_AFTER */  row_BEFORE, /* INDEX_BEFORE */  row_BEFORE_AND_AFTER, /* INDEX_BEFORE_AND_AFTER */  row_ZERO_WIDTH_SPACE, /* INDEX_ZERO_WIDTH_SPACE */  row_COMBINING_MARK, /* INDEX_COMBINING_MARK */  row_WORD_JOINER /* INDEX_WORD_JOINER */};/* Map GUnicodeBreakType to table indexes */static const int line_break_indexes[] = {  INDEX_MANDATORY,  INDEX_CARRIAGE_RETURN,  INDEX_LINE_FEED,  INDEX_COMBINING_MARK,  INDEX_SURROGATE,  INDEX_ZERO_WIDTH_SPACE,  INDEX_INSEPARABLE,  INDEX_NON_BREAKING_GLUE,  INDEX_CONTINGENT,  INDEX_SPACE,  INDEX_AFTER,  INDEX_BEFORE,  INDEX_BEFORE_AND_AFTER,  INDEX_HYPHEN,  INDEX_NON_STARTER,  INDEX_OPEN_PUNCTUATION,  INDEX_CLOSE_PUNCTUATION,  INDEX_QUOTATION,  INDEX_EXCLAMATION,  INDEX_IDEOGRAPHIC,  INDEX_NUMERIC,  INDEX_INFIX_SEPARATOR,  INDEX_SYMBOL,  INDEX_ALPHABETIC,  INDEX_PREFIX,  INDEX_POSTFIX,  INDEX_COMPLEX_CONTEXT,  INDEX_AMBIGUOUS,  INDEX_UNKNOWN,  INDEX_NEXT_LINE,  INDEX_WORD_JOINER,  INDEX_HANGUL_L_JAMO,  INDEX_HANGUL_V_JAMO,  INDEX_HANGUL_T_JAMO,  INDEX_HANGUL_LV_SYLLABLE,  INDEX_HANGUL_LVT_SYLLABLE};#define BREAK_TYPE_SAFE(btype)            \	 (btype < G_N_ELEMENTS(line_break_indexes) ? btype : G_UNICODE_BREAK_UNKNOWN)#define BREAK_INDEX(btype)                \	 (line_break_indexes[(btype)])#define BREAK_ROW(before_type)            \	 (line_break_rows[BREAK_INDEX (before_type)])#define BREAK_OP(before_type, after_type) \	 (BREAK_ROW (before_type)[BREAK_INDEX (after_type)])#define IN_BREAK_TABLE(btype)             \	 (btype < G_N_ELEMENTS(line_break_indexes) && BREAK_INDEX(btype) < INDEX_END_OF_TABLE)/* * Hangul Conjoining Jamo handling. * * The way we implement it is just a bit different from TR14, * but produces the same results. * The same algorithm is also used in TR29 for cluster boundaries. * *//* An enum that works as the states of the Hangul syllables system. **/typedef enum{  JAMO_L,	/* G_UNICODE_BREAK_HANGUL_L_JAMO */  JAMO_V,	/* G_UNICODE_BREAK_HANGUL_V_JAMO */  JAMO_T,	/* G_UNICODE_BREAK_HANGUL_T_JAMO */  JAMO_LV,	/* G_UNICODE_BREAK_HANGUL_LV_SYLLABLE */  JAMO_LVT,	/* G_UNICODE_BREAK_HANGUL_LVT_SYLLABLE */  NO_JAMO	/* Other */} JamoType;/* There are Hangul syllables encoded as characters, that act like a * sequence of Jamos. For each character we define a JamoType * that the character starts with, and one that it ends with.  This * decomposes JAMO_LV and JAMO_LVT to simple other JAMOs.  So for * example, a character with LineBreak type * G_UNICODE_BREAK_HANGUL_LV_SYLLABLE has start=JAMO_L and end=JAMO_V. */typedef struct _CharJamoProps{  JamoType start, end;} CharJamoProps;/* Map from JamoType to CharJamoProps that hold only simple * JamoTypes (no LV or LVT) or none. */static const CharJamoProps HangulJamoProps[] = {  {JAMO_L, JAMO_L},	/* JAMO_L */  {JAMO_V, JAMO_V},	/* JAMO_V */  {JAMO_T, JAMO_T},	/* JAMO_T */  {JAMO_L, JAMO_V},	/* JAMO_LV */  {JAMO_L, JAMO_T},	/* JAMO_LVT */  {NO_JAMO, NO_JAMO}	/* NO_JAMO */};/* A character forms a syllable with the previous character if and only if: * JamoType(this) is not NO_JAMO and: * * HangulJamoProps[JamoType(prev)].end and * HangulJamoProps[JamoType(this)].start are equal, * or the former is one less than the latter. */#define IS_JAMO(btype)              \	((btype >= G_UNICODE_BREAK_HANGUL_L_JAMO) && \	 (btype <= G_UNICODE_BREAK_HANGUL_LVT_SYLLABLE))#define JAMO_TYPE(btype)      \	(IS_JAMO(btype) ? (btype - G_UNICODE_BREAK_HANGUL_L_JAMO) : NO_JAMO)/* "virama script" is just an optimization; it includes a bunch of * scripts without viramas in them */#define VIRAMA_SCRIPT(wc)        ((wc) >= 0x0901 && (wc) <= 0x17FF)#define VIRAMA(wc) ((wc) == 0x094D || \		    (wc) == 0x09CD || \		    (wc) == 0x0A4D || \		    (wc) == 0x0ACD || \		    (wc) == 0x0B4D || \		    (wc) == 0x0BCD || \		    (wc) == 0x0C4D || \		    (wc) == 0x0CCD || \		    (wc) == 0x0D4D || \		    (wc) == 0x0DCA || \

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -