LCOV - code coverage report
Current view: top level - Unicode - is_Ligature.c (source / functions) Hit Total Coverage
Test: FontForge coverage report 2017-08-04 01:21:11+02:00 (commit d35f7e4107a9e1db65cce47c468fcc914cecb8fd) Lines: 111 195 56.9 %
Date: 2017-08-04 Functions: 21 31 67.7 %

          Line data    Source code
       1             : /*
       2             : Copyright: 2012 Barry Schwartz
       3             :     Create is_Ligature.c (using a python script) to test for Vulgar fractions
       4             : Copyright: 2016 Joe Da Silva
       5             :     Re-write is_Ligature.c to test for ligatures, Vulgar and Other-fractions.
       6             : Copyright: 2016 Gioele Barabucci
       7             :     Simplify makeutype.c code. Split is_Ligature.c, create is_Ligature_data.h
       8             : License: BSD-3-clause
       9             : Contributions:
      10             : */
      11             : 
      12             : #include "basics.h"   /* for non-standard uint{16,32} typedefs */
      13             : #include "is_Ligature_data.h"
      14             : #include "utype.h"
      15             : #include "chardata.h"
      16             : #include <stdlib.h>
      17             : 
      18         254 : static int compare_codepoints16(const void *uCode1, const void *uCode2) {
      19         254 :     const uint16 *cp1 = (const uint16 *)(uCode1);
      20         254 :     const uint16 *cp2 = (const uint16 *)(uCode2);
      21         254 :     return( (*cp1 < *cp2) ? -1 : ((*cp1 == *cp2) ? 0 : 1) );
      22             : }
      23             : 
      24           4 : static int compare_codepoints32(const void *uCode1, const void *uCode2) {
      25           4 :     const uint32 *cp1 = (const uint32 *)(uCode1);
      26           4 :     const uint32 *cp2 = (const uint32 *)(uCode2);
      27           4 :     return( (*cp1 < *cp2) ? -1 : ((*cp1 == *cp2) ? 0 : 1) );
      28             : }
      29             : 
      30           2 : int LigatureCount(void) {
      31           2 :     return( FF_ligatureTOTAL );
      32             : }
      33             : 
      34           2 : int VulgarFractionCount(void) {
      35           2 :     return( FF_vulgfracTOTAL );
      36             : }
      37             : 
      38           2 : int OtherFractionCount(void) {
      39           2 :     return( FF_fractionTOTAL );
      40             : }
      41             : 
      42           2 : int FractionCount(void) {
      43           2 :     return( FF_vulgfracTOTAL + FF_fractionTOTAL );
      44             : }
      45             : 
      46          14 : int32 Ligature_get_U(int n) {
      47          14 :     if ( n < 0 || n >= FF_ligatureTOTAL )
      48           2 :         return( -1 );
      49          12 :     if ( n < FF_ligatureTOTAL16 )
      50          12 :         return( (int32)(ligature16[n]) );
      51             :     else
      52           0 :         return( (int32)(ligature32[n-FF_ligatureTOTAL16]) );
      53             : }
      54             : 
      55           8 : int32 VulgFrac_get_U(int n) {
      56           8 :     if ( n < 0 || n >= FF_vulgfracTOTAL )
      57           0 :         return( -1 );
      58           8 :     if ( n < FF_vulgfracTOTAL16 )
      59           8 :         return( (int32)(vulgfrac16[n]) );
      60             :     else
      61           0 :         return( (int32)(vulgfrac32[n-FF_vulgfracTOTAL16]) );
      62             : }
      63             : 
      64           2 : int32 Fraction_get_U(int n) {
      65           2 :     if ( n < 0 || n >= FF_fractionTOTAL )
      66           0 :         return( -1 );
      67           2 :     if ( n < FF_fractionTOTAL16 )
      68           0 :         return( (int32)(fraction16[n]) );
      69             :     else
      70           2 :         return( (int32)(fraction32[n-FF_fractionTOTAL16]) );
      71             : }
      72             : 
      73          30 : int Ligature_find_N(uint32 uCode) {
      74             :     uint16 uCode16, *p16;
      75             :     uint32 *p32;
      76          30 :     int n=-1;
      77             : 
      78          60 :     if ( uCode < FF_ligature16FIRST || uCode > FF_ligature32LAST || \
      79          56 :          ((uCode < FF_UTYPE_MAXC) && (isligorfrac(uCode)==0)) )
      80           4 :         return( -1 );
      81          26 :     if ( uCode <= FF_ligature16LAST ) {
      82          22 :         uCode16 = uCode;
      83          22 :         p16 = (uint16 *)(bsearch(&uCode16, ligature16, FF_ligatureTOTAL16, \
      84             :                                 sizeof(uint16), compare_codepoints16));
      85          22 :         if ( p16 ) n = p16 - ligature16;
      86           4 :     } else if ( uCode >= FF_ligature32FIRST ) {
      87           4 :         p32 = (uint32 *)(bsearch(&uCode, ligature32, FF_ligatureTOTAL32, \
      88             :                                 sizeof(uint32), compare_codepoints32));
      89           4 :         if ( p32 ) n = p32 - ligature32 + FF_ligatureTOTAL16;
      90             :     }
      91          26 :     return( n );
      92             : }
      93             : 
      94          16 : int VulgFrac_find_N(uint32 uCode) {
      95             :     uint16 uCode16, *p16;
      96             :     uint32 *p32;
      97          16 :     int n=-1;
      98             : 
      99          32 :     if ( uCode < FF_vulgfrac16FIRST || uCode > FF_vulgfrac32LAST || \
     100          32 :          ((uCode < FF_UTYPE_MAXC) && (isligorfrac(uCode)==0)) )
     101           0 :         return( -1 );
     102          16 :     if (uCode <= FF_vulgfrac16LAST) {
     103          16 :         uCode16 = uCode;
     104          16 :         p16 = (uint16 *)(bsearch(&uCode16, vulgfrac16, FF_vulgfracTOTAL16, \
     105             :                                 sizeof(uint16), compare_codepoints16));
     106          16 :         if ( p16 ) n = p16 - vulgfrac16;
     107           0 :     } else if ( uCode >= FF_vulgfrac32FIRST ) {
     108           0 :         p32 = (uint32 *)(bsearch(&uCode, vulgfrac32, FF_vulgfracTOTAL32, \
     109             :                                 sizeof(uint32), compare_codepoints32));
     110           0 :         if (p32) n = p32 - vulgfrac32 + FF_vulgfracTOTAL16;
     111             :     }
     112          16 :     return( n );
     113             : }
     114             : 
     115           2 : int Fraction_find_N(uint32 uCode) {
     116             :     uint16 uCode16, *p16;
     117             :     uint32 *p32;
     118           2 :     int n=-1;
     119             : 
     120           4 :     if ( uCode < FF_fractionTOTAL16 || uCode > FF_fraction32LAST || \
     121           4 :          ((uCode < FF_UTYPE_MAXC) && (isligorfrac(uCode)==0)) )
     122           0 :         return( -1 );
     123           2 :     if ( uCode <= FF_fraction16LAST ) {
     124           2 :         uCode16 = uCode;
     125           2 :         p16 = (uint16 *)(bsearch(&uCode16, fraction16, FF_fractionTOTAL16, \
     126             :                                 sizeof(uint16), compare_codepoints16));
     127           2 :         if ( p16 ) n = p16 - fraction16;
     128           0 :     } else if ( uCode >= FF_fraction32FIRST ) {
     129           0 :         p32 = (uint32 *)(bsearch(&uCode, fraction32, FF_fractionTOTAL32, \
     130             :                                 sizeof(uint32), compare_codepoints32));
     131           0 :         if ( p32 ) n = p32 - fraction32 + FF_fractionTOTAL16;
     132             :     }
     133           2 :     return( n );
     134             : }
     135             : 
     136             : /* FontForge has a built-in internal table of ligatures. This function returns c */
     137             : /* for ligature[n], so for example if ligature[n] is 'ae' then c is 2 {a=0,e=1}, */
     138             : /* or if ligature[n] is 'ffi' then c is 3 {f=0,f=1,i=2}. Allowed range of n is 0 */
     139             : /* to n < LigatureCount() (the size of the internal table), otherwise return -1. */
     140          30 : int Ligature_alt_getC(int n) {
     141             :     int i,j;
     142             : 
     143          30 :     if ( n < 0 || n >= FF_ligatureTOTAL )
     144           0 :         return( -1 );
     145          30 :     if ( (i=ligatureAltI[n])&0x80 ) {
     146          12 :         j = i & 0x7f;
     147          58 :         for ( i=0; j; j=j>>1 )
     148          46 :             if ( j&1 ) ++i;
     149          12 :         return( i );
     150          18 :     } else if ( i < FF_ligatureTIS ) {
     151          18 :         return( ligatureAltIs[i+1] - ligatureAltIs[i] );
     152             :     } else {
     153           0 :         i -= FF_ligatureTIS;
     154           0 :         return( ligatureAltIl[i+1] - ligatureAltIl[i] );
     155             :     }
     156             : }
     157             : 
     158             : /* This function returns the unicode value for ligature[n][a]. Errors return -1. */
     159             : /* allowed ranges: {0 <= n < LigatureCount()} & {0 <= a < Ligature_alt_getC(n)}. */
     160             : /* For example, if ligature[n]='ae', then LigatureCount(n)=2 and the results are */
     161             : /* alternate values of 'a'=Ligature_alt_getV(n,0) and 'e'=Ligature_alt_getV(n,1) */
     162          20 : int32 Ligature_alt_getV(int n,int a) {
     163             :     int i,j;
     164             :     const unichar_t *upt;
     165             :     int32 u;
     166             : 
     167          20 :     if ( n < 0 || n >= FF_ligatureTOTAL || a<0 || a>=Ligature_alt_getC(n) )
     168           4 :         return( -1 );
     169          16 :     if ( (i=ligatureAltI[n])&0x80 ) {
     170           4 :         j = i & 0x7f;
     171          18 :         for ( i=0; a; ++i )
     172          14 :             if ( j&(1<<i) ) --a;
     173           4 :         u = Ligature_get_U(n);
     174           4 :         upt = unicode_alternates[u>>8][u&0xff];
     175           4 :         return( (int32)(upt[i]) );
     176          12 :     } else if ( i < FF_ligatureTIS ) {
     177          12 :         i = ligatureAltIs[i];
     178          12 :         u = ligatureAlt16[i+a];
     179          12 :         return( u );
     180             :     } else {
     181           0 :         i -= FF_ligatureTIS;
     182           0 :         i = ligatureAltIl[i];
     183           0 :         u = ligatureAlt32[i+a];
     184           0 :         return( u );
     185             :     }
     186             : }
     187             : 
     188             : /* This returns similar results like Ligature_alt_getC(n) but uses unicode input */
     189             : /* uCode instead of ligature[n]. This isn't as speedy as c=Ligature_alt_getC(n). */
     190           6 : int LigatureU_alt_getC(uint32 uCode) {
     191           6 :     return( Ligature_alt_getC(Ligature_find_N(uCode)) );
     192             : }
     193             : 
     194           6 : int32 LigatureU_alt_getV(uint32 uCode,int a) {
     195             :     int32 n;
     196             : 
     197           6 :     if ( (n=Ligature_find_N(uCode))<0 )
     198           0 :         return( -1 );
     199           6 :     return( Ligature_alt_getV(n,a) );
     200             : }
     201             : 
     202          14 : int VulgFrac_alt_getC(int n) {
     203             :     int i,j;
     204             : 
     205          14 :     if ( n < 0 || n >= FF_vulgfracTOTAL )
     206           2 :         return( -1 );
     207          12 :     if ( (i=vulgfracAltI[n])&0x80 ) {
     208          12 :         j = i & 0x7f;
     209          54 :         for ( i=0; j; j=j>>1 )
     210          42 :             if ( j&1 ) ++i;
     211          12 :         return( i );
     212           0 :     } else if ( i < FF_vulgfracTIS ) {
     213           0 :         return( vulgfracAltIs[i+1] - vulgfracAltIs[i] );
     214             :     } else {
     215           0 :         i -= FF_vulgfracTIS;
     216           0 :         return( vulgfracAltIl[i+1] - vulgfracAltIl[i] );
     217             :     }
     218             : }
     219             : 
     220           8 : int32 VulgFrac_alt_getV(int n,int a) {
     221             :     int i,j;
     222             :     const unichar_t *upt;
     223             :     int32 u;
     224             : 
     225           8 :     if ( n < 0 || n >= FF_vulgfracTOTAL || a<0 || a>=VulgFrac_alt_getC(n) )
     226           0 :         return( -1 );
     227           8 :     if ( (i=vulgfracAltI[n])&0x80 ) {
     228           8 :         j = i & 0x7f;
     229          22 :         for ( i=0; a; ++i )
     230          14 :             if ( j&(1<<i) ) --a;
     231           8 :         u = VulgFrac_get_U(n);
     232           8 :         upt = unicode_alternates[u>>8][u&0xff];
     233           8 :         return( (int32)(upt[i]) );
     234           0 :     } else if ( i < FF_vulgfracTIS ) {
     235           0 :         i = vulgfracAltIs[i];
     236           0 :         u = vulgfracAlt16[i+a];
     237           0 :         return( u );
     238             :     } else {
     239           0 :         i -= FF_vulgfracTIS;
     240           0 :         i = vulgfracAltIl[i];
     241           0 :         u = vulgfracAlt32[i+a];
     242           0 :         return( u );
     243             :     }
     244             : }
     245             : 
     246           0 : int VulgFracU_alt_getC(uint32 uCode) {
     247           0 :     return( VulgFrac_alt_getC(VulgFrac_find_N(uCode)) );
     248             : }
     249             : 
     250           0 : int32 VulgFracU_alt_getV(uint32 uCode,int a) {
     251             :     int32 n;
     252             : 
     253           0 :     if ( (n=VulgFrac_find_N(uCode))< 0 )
     254           0 :         return( -1 );
     255           0 :     return( VulgFrac_alt_getV(n,a) );
     256             : }
     257             : 
     258           0 : int Fraction_alt_getC(int n) {
     259             :     int i,j;
     260             : 
     261           0 :     if ( n < 0 || n >= FF_fractionTOTAL )
     262           0 :         return( -1 );
     263           0 :     if ( (i=fractionAltI[n])&0x80 ) {
     264           0 :         j = i & 0x7f;
     265           0 :         for ( i=0; j; j=j>>1 )
     266           0 :             if ( j&1 ) ++i;
     267           0 :         return( i );
     268           0 :     } else if ( i < FF_fractionTIS ) {
     269           0 :         return( fractionAltIs[i+1] - fractionAltIs[i] );
     270             :     } else {
     271           0 :         i -= FF_fractionTIS;
     272           0 :         return( fractionAltIl[i+1] - fractionAltIl[i] );
     273             :     }
     274             : }
     275             : 
     276           0 : int32 Fraction_alt_getV(int n,int a) {
     277             :     int i,j;
     278             :     const unichar_t *upt;
     279             :     int32 u;
     280             : 
     281           0 :     if ( n < 0 || n >= FF_fractionTOTAL || a<0 || a>=Fraction_alt_getC(n) )
     282           0 :         return( -1 );
     283           0 :     if ( (i=fractionAltI[n])&0x80 ) {
     284           0 :         j = i & 0x7f;
     285           0 :         for ( i=0; a; ++i )
     286           0 :             if ( j&(1<<i) ) --a;
     287           0 :         u = Fraction_get_U(n);
     288           0 :         upt = unicode_alternates[u>>8][u&0xff];
     289           0 :         return( (int32)(upt[i]) );
     290           0 :     } else if ( i < FF_fractionTIS ) {
     291           0 :         i = fractionAltIs[i];
     292           0 :         u = fractionAlt16[i+a];
     293           0 :         return( u );
     294             :     } else {
     295           0 :         i -= FF_fractionTIS;
     296           0 :         i = fractionAltIl[i];
     297           0 :         u = fractionAlt16[i+a];
     298           0 :         return( u );
     299             :     }
     300             : }
     301             : 
     302           0 : int FractionU_alt_getC(uint32 uCode) {
     303           0 :     return( Fraction_alt_getC(Fraction_find_N(uCode)) );
     304             : }
     305             : 
     306           0 : int32 FractionU_alt_getV(uint32 uCode,int a) {
     307             :     int32 n;
     308             : 
     309           0 :     if ( (n=Fraction_find_N(uCode))< 0 )
     310           0 :         return( -1 );
     311           0 :     return( Fraction_alt_getV(n,a) );
     312             : }
     313             : /* Boolean-style tests (found==0) to see if your codepoint value is listed */
     314             : /* unicode.org codepoints for ligatures, vulgar fractions, other fractions */
     315             : 
     316           4 : int is_LIGATURE(uint32 codepoint) {
     317           4 :     return( Ligature_find_N(codepoint)<0 );
     318             : }
     319             : 
     320           8 : int is_VULGAR_FRACTION(uint32 codepoint) {
     321           8 :     return( VulgFrac_find_N(codepoint)<0 );
     322             : }
     323             : 
     324           2 : int is_OTHER_FRACTION(uint32 codepoint) {
     325           2 :     return( Fraction_find_N(codepoint)<0 );
     326             : }
     327             : 
     328           0 : int is_FRACTION(uint32 codepoint) {
     329           0 :     return( VulgFrac_find_N(codepoint)<0 && Fraction_find_N(codepoint)<0 );
     330             : }
     331             : 
     332           0 : int is_LIGATURE_or_VULGAR_FRACTION(uint32 codepoint) {
     333           0 :     return( Ligature_find_N(codepoint)<0 && VulgFrac_find_N(codepoint)<0 );
     334             : }
     335             : 
     336           0 : int is_LIGATURE_or_OTHER_FRACTION(uint32 codepoint) {
     337           0 :     return( Ligature_find_N(codepoint)<0 && Fraction_find_N(codepoint)<0 );
     338             : }
     339             : 
     340           0 : int is_LIGATURE_or_FRACTION(uint32 codepoint) {
     341           0 :     return( Ligature_find_N(codepoint)<0 && VulgFrac_find_N(codepoint)<0 && Fraction_find_N(codepoint)<0 );
     342             : }
     343             : 

Generated by: LCOV version 1.10