1cimport h3lib 2from .h3lib cimport bool, H3int 3 4from .util cimport ( 5 check_cell, 6 check_edge, 7 check_res, 8 create_ptr, 9 create_mv, 10) 11 12from .util import H3ValueError 13 14cpdef bool are_neighbors(H3int h1, H3int h2): 15 check_cell(h1) 16 check_cell(h2) 17 18 return h3lib.h3IndexesAreNeighbors(h1, h2) == 1 19 20 21cpdef H3int edge(H3int origin, H3int destination) except 1: 22 check_cell(origin) 23 check_cell(destination) 24 25 if h3lib.h3IndexesAreNeighbors(origin, destination) != 1: 26 s = 'Cells are not neighbors: {} and {}' 27 s = s.format(hex(origin), hex(destination)) 28 raise H3ValueError(s) 29 30 return h3lib.getH3UnidirectionalEdge(origin, destination) 31 32 33cpdef bool is_edge(H3int e): 34 return h3lib.h3UnidirectionalEdgeIsValid(e) == 1 35 36cpdef H3int edge_origin(H3int e) except 1: 37 # without the check, with an invalid input, the function will just return 0 38 check_edge(e) 39 40 return h3lib.getOriginH3IndexFromUnidirectionalEdge(e) 41 42cpdef H3int edge_destination(H3int e) except 1: 43 check_edge(e) 44 45 return h3lib.getDestinationH3IndexFromUnidirectionalEdge(e) 46 47cpdef (H3int, H3int) edge_cells(H3int e) except *: 48 check_edge(e) 49 50 return edge_origin(e), edge_destination(e) 51 52cpdef H3int[:] edges_from_cell(H3int origin): 53 """ Returns the 6 (or 5 for pentagons) directed edges 54 for the given origin cell 55 """ 56 check_cell(origin) 57 58 ptr = create_ptr(6) 59 h3lib.getH3UnidirectionalEdgesFromHexagon(origin, ptr) 60 mv = create_mv(ptr, 6) 61 62 return mv 63 64 65cpdef double mean_edge_length(int resolution, unit='km') except -1: 66 check_res(resolution) 67 68 length = h3lib.edgeLengthKm(resolution) 69 70 # todo: multiple units 71 convert = { 72 'km': 1.0, 73 'm': 1000.0 74 } 75 76 try: 77 length *= convert[unit] 78 except: 79 raise H3ValueError('Unknown unit: {}'.format(unit)) 80 81 return length 82 83 84cpdef double edge_length(H3int e, unit='km') except -1: 85 check_edge(e) 86 87 # todo: maybe kick this logic up to the python level 88 # it might be a little cleaner, because we can do the "switch statement" 89 # with a dict, but would require exposing more C functions 90 91 if unit == 'rads': 92 length = h3lib.exactEdgeLengthRads(e) 93 elif unit == 'km': 94 length = h3lib.exactEdgeLengthKm(e) 95 elif unit == 'm': 96 length = h3lib.exactEdgeLengthM(e) 97 else: 98 raise H3ValueError('Unknown unit: {}'.format(unit)) 99 100 return length 101