xtgeo 4.14.1__cp313-cp313-win_amd64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (122) hide show
  1. cxtgeo.py +558 -0
  2. cxtgeoPYTHON_wrap.c +19537 -0
  3. xtgeo/__init__.py +248 -0
  4. xtgeo/_cxtgeo.cp313-win_amd64.pyd +0 -0
  5. xtgeo/_internal.cp313-win_amd64.pyd +0 -0
  6. xtgeo/common/__init__.py +19 -0
  7. xtgeo/common/_angles.py +29 -0
  8. xtgeo/common/_xyz_enum.py +50 -0
  9. xtgeo/common/calc.py +396 -0
  10. xtgeo/common/constants.py +30 -0
  11. xtgeo/common/exceptions.py +42 -0
  12. xtgeo/common/log.py +93 -0
  13. xtgeo/common/sys.py +166 -0
  14. xtgeo/common/types.py +18 -0
  15. xtgeo/common/version.py +34 -0
  16. xtgeo/common/xtgeo_dialog.py +604 -0
  17. xtgeo/cube/__init__.py +9 -0
  18. xtgeo/cube/_cube_export.py +214 -0
  19. xtgeo/cube/_cube_import.py +532 -0
  20. xtgeo/cube/_cube_roxapi.py +180 -0
  21. xtgeo/cube/_cube_utils.py +287 -0
  22. xtgeo/cube/_cube_window_attributes.py +273 -0
  23. xtgeo/cube/cube1.py +1023 -0
  24. xtgeo/grid3d/__init__.py +15 -0
  25. xtgeo/grid3d/_ecl_grid.py +778 -0
  26. xtgeo/grid3d/_ecl_inte_head.py +152 -0
  27. xtgeo/grid3d/_ecl_logi_head.py +71 -0
  28. xtgeo/grid3d/_ecl_output_file.py +81 -0
  29. xtgeo/grid3d/_egrid.py +1004 -0
  30. xtgeo/grid3d/_find_gridprop_in_eclrun.py +625 -0
  31. xtgeo/grid3d/_grdecl_format.py +309 -0
  32. xtgeo/grid3d/_grdecl_grid.py +400 -0
  33. xtgeo/grid3d/_grid3d.py +29 -0
  34. xtgeo/grid3d/_grid3d_fence.py +284 -0
  35. xtgeo/grid3d/_grid3d_utils.py +228 -0
  36. xtgeo/grid3d/_grid_boundary.py +76 -0
  37. xtgeo/grid3d/_grid_etc1.py +1683 -0
  38. xtgeo/grid3d/_grid_export.py +222 -0
  39. xtgeo/grid3d/_grid_hybrid.py +50 -0
  40. xtgeo/grid3d/_grid_import.py +79 -0
  41. xtgeo/grid3d/_grid_import_ecl.py +101 -0
  42. xtgeo/grid3d/_grid_import_roff.py +135 -0
  43. xtgeo/grid3d/_grid_import_xtgcpgeom.py +375 -0
  44. xtgeo/grid3d/_grid_refine.py +258 -0
  45. xtgeo/grid3d/_grid_roxapi.py +292 -0
  46. xtgeo/grid3d/_grid_translate_coords.py +154 -0
  47. xtgeo/grid3d/_grid_wellzone.py +165 -0
  48. xtgeo/grid3d/_gridprop_export.py +202 -0
  49. xtgeo/grid3d/_gridprop_import_eclrun.py +164 -0
  50. xtgeo/grid3d/_gridprop_import_grdecl.py +132 -0
  51. xtgeo/grid3d/_gridprop_import_roff.py +52 -0
  52. xtgeo/grid3d/_gridprop_import_xtgcpprop.py +168 -0
  53. xtgeo/grid3d/_gridprop_lowlevel.py +171 -0
  54. xtgeo/grid3d/_gridprop_op1.py +272 -0
  55. xtgeo/grid3d/_gridprop_roxapi.py +301 -0
  56. xtgeo/grid3d/_gridprop_value_init.py +140 -0
  57. xtgeo/grid3d/_gridprops_import_eclrun.py +344 -0
  58. xtgeo/grid3d/_gridprops_import_roff.py +83 -0
  59. xtgeo/grid3d/_roff_grid.py +470 -0
  60. xtgeo/grid3d/_roff_parameter.py +303 -0
  61. xtgeo/grid3d/grid.py +3010 -0
  62. xtgeo/grid3d/grid_properties.py +699 -0
  63. xtgeo/grid3d/grid_property.py +1313 -0
  64. xtgeo/grid3d/types.py +15 -0
  65. xtgeo/interfaces/rms/__init__.py +18 -0
  66. xtgeo/interfaces/rms/_regular_surface.py +460 -0
  67. xtgeo/interfaces/rms/_rms_base.py +100 -0
  68. xtgeo/interfaces/rms/_rmsapi_package.py +69 -0
  69. xtgeo/interfaces/rms/rmsapi_utils.py +438 -0
  70. xtgeo/io/__init__.py +1 -0
  71. xtgeo/io/_file.py +603 -0
  72. xtgeo/metadata/__init__.py +17 -0
  73. xtgeo/metadata/metadata.py +435 -0
  74. xtgeo/roxutils/__init__.py +7 -0
  75. xtgeo/roxutils/_roxar_loader.py +54 -0
  76. xtgeo/roxutils/_roxutils_etc.py +122 -0
  77. xtgeo/roxutils/roxutils.py +207 -0
  78. xtgeo/surface/__init__.py +20 -0
  79. xtgeo/surface/_regsurf_boundary.py +26 -0
  80. xtgeo/surface/_regsurf_cube.py +210 -0
  81. xtgeo/surface/_regsurf_cube_window.py +391 -0
  82. xtgeo/surface/_regsurf_cube_window_v2.py +297 -0
  83. xtgeo/surface/_regsurf_cube_window_v3.py +360 -0
  84. xtgeo/surface/_regsurf_export.py +388 -0
  85. xtgeo/surface/_regsurf_grid3d.py +275 -0
  86. xtgeo/surface/_regsurf_gridding.py +347 -0
  87. xtgeo/surface/_regsurf_ijxyz_parser.py +278 -0
  88. xtgeo/surface/_regsurf_import.py +347 -0
  89. xtgeo/surface/_regsurf_lowlevel.py +122 -0
  90. xtgeo/surface/_regsurf_oper.py +538 -0
  91. xtgeo/surface/_regsurf_utils.py +81 -0
  92. xtgeo/surface/_surfs_import.py +43 -0
  93. xtgeo/surface/_zmap_parser.py +138 -0
  94. xtgeo/surface/regular_surface.py +3043 -0
  95. xtgeo/surface/surfaces.py +276 -0
  96. xtgeo/well/__init__.py +24 -0
  97. xtgeo/well/_blockedwell_roxapi.py +241 -0
  98. xtgeo/well/_blockedwells_roxapi.py +68 -0
  99. xtgeo/well/_well_aux.py +30 -0
  100. xtgeo/well/_well_io.py +327 -0
  101. xtgeo/well/_well_oper.py +483 -0
  102. xtgeo/well/_well_roxapi.py +304 -0
  103. xtgeo/well/_wellmarkers.py +486 -0
  104. xtgeo/well/_wells_utils.py +158 -0
  105. xtgeo/well/blocked_well.py +220 -0
  106. xtgeo/well/blocked_wells.py +134 -0
  107. xtgeo/well/well1.py +1516 -0
  108. xtgeo/well/wells.py +211 -0
  109. xtgeo/xyz/__init__.py +6 -0
  110. xtgeo/xyz/_polygons_oper.py +272 -0
  111. xtgeo/xyz/_xyz.py +758 -0
  112. xtgeo/xyz/_xyz_data.py +646 -0
  113. xtgeo/xyz/_xyz_io.py +737 -0
  114. xtgeo/xyz/_xyz_lowlevel.py +42 -0
  115. xtgeo/xyz/_xyz_oper.py +613 -0
  116. xtgeo/xyz/_xyz_roxapi.py +766 -0
  117. xtgeo/xyz/points.py +698 -0
  118. xtgeo/xyz/polygons.py +827 -0
  119. xtgeo-4.14.1.dist-info/METADATA +146 -0
  120. xtgeo-4.14.1.dist-info/RECORD +122 -0
  121. xtgeo-4.14.1.dist-info/WHEEL +5 -0
  122. xtgeo-4.14.1.dist-info/licenses/LICENSE.md +165 -0
@@ -0,0 +1,207 @@
1
+ """Module for simplifying various operation in the Roxar python interface."""
2
+
3
+ from packaging.version import parse as versionparse
4
+
5
+ from xtgeo.common.log import null_logger
6
+ from xtgeo.common.xtgeo_dialog import XTGeoDialog
7
+
8
+ from . import _roxutils_etc
9
+ from ._roxar_loader import roxar
10
+
11
+ xtg = XTGeoDialog()
12
+ logger = null_logger(__name__)
13
+
14
+
15
+ class RoxUtils(object):
16
+ """Class RoxUtils, for accessing project level methods::
17
+
18
+ import xtgeo
19
+
20
+ xr = xtgeo.RoxUtils(project)
21
+ xr.create_horizon_category('DS_extracted_run3')
22
+ xr.delete_horizon_category('DS_extracted_run2')
23
+
24
+ The project itself can be a reference to an existing project, typically
25
+ the magic ``project`` wording inside RMS python,
26
+ or a file path to a RMS project (for external access).
27
+
28
+ Args:
29
+ project (roxar.Project or str): Reference to a RMS project
30
+ either an existing instance or a RMS project folder path.
31
+ readonly (bool). Default is False. If readonly, then it cannot be
32
+ saved to this project (which is the case for "secondary" projects).
33
+
34
+ Examples::
35
+
36
+ import xgeo
37
+ path = '/some/path/to/rmsprject.rmsx'
38
+
39
+ ext = xtgeo.RoxUtils(path, readonly=True)
40
+ # ...do something
41
+ ext.safe_close()
42
+
43
+ """
44
+
45
+ def __init__(self, project, readonly=False):
46
+ self._project = None
47
+
48
+ self._version = roxar.__version__
49
+
50
+ if versionparse(self._version) < versionparse("1.5"):
51
+ raise RuntimeError("XTGeo >= 3.0 requires Roxar API >= 1.5")
52
+
53
+ self._roxexternal = True
54
+
55
+ self._versions = {
56
+ "1.0": ["10.0.x"],
57
+ "1.1": ["10.1.0", "10.1.1", "10.1.2"],
58
+ "1.1.1": ["10.1.3"],
59
+ "1.2": ["11.0.0"],
60
+ "1.2.1": ["11.0.1"],
61
+ "1.3": ["11.1.0", "11.1.1", "11.1.2"],
62
+ "1.4": ["12.0.0", "12.0.1", "12.0.2"],
63
+ "1.5": ["12.1"],
64
+ "1.6": ["13.0"],
65
+ "1.7": ["13.1"],
66
+ }
67
+
68
+ if project is not None and isinstance(project, str):
69
+ projectname = project
70
+ self._project = roxar.Project.open(projectname, readonly=readonly)
71
+ logger.info("Open RMS project from %s", projectname)
72
+
73
+ elif isinstance(project, roxar.Project):
74
+ # this will happen for _current_ project inside RMS or if
75
+ # project is opened already e.g. by roxar.Project.open(). In the latter
76
+ # case, the user should also close the project by project.close() as
77
+ # an explicit action.
78
+
79
+ self._roxexternal = False
80
+ self._project = project
81
+ logger.info("RMS project instance is already open as <%s>", project)
82
+ else:
83
+ raise RuntimeError("Project is not valid")
84
+
85
+ @property
86
+ def roxversion(self):
87
+ """Roxar API version (read only)"""
88
+ return self._version
89
+
90
+ @property
91
+ def project(self):
92
+ """The Roxar project instance (read only)"""
93
+ return self._project
94
+
95
+ def safe_close(self):
96
+ """Close the project but only if roxarapps (external) mode, i.e.
97
+ not current RMS project
98
+
99
+ In case roxar.Project.open() is done explicitly, safe_close() will do nothing.
100
+
101
+ """
102
+ if self._roxexternal:
103
+ try:
104
+ self._project.close()
105
+ logger.info("RMS project instance is closed")
106
+ except TypeError as msg:
107
+ xtg.warn(msg)
108
+ else:
109
+ logger.info("Close request, but skip for good reasons...")
110
+ logger.debug("... either in RMS GUI or in a sequence of running roxarapps")
111
+
112
+ def version_required(self, targetversion):
113
+ """Defines a minimum ROXAPI version for some feature (True or False).
114
+
115
+ Args:
116
+ targetversion (str): Minimum version to compare with.
117
+
118
+ Example::
119
+
120
+ rox = RoxUtils(project)
121
+ if rox.version_required('1.5'):
122
+ somefunction()
123
+ else:
124
+ print('Not supported in this version')
125
+
126
+ """
127
+ return versionparse(self._version) >= versionparse(targetversion)
128
+
129
+ def rmsversion(self, apiversion):
130
+ """Get the actual RMS version(s) given an API version.
131
+
132
+ Args:
133
+ apiversion (str): ROXAPI version to ask for
134
+
135
+ Returns:
136
+ A list of RMS version(s) for the given API version, None if
137
+ not any match.
138
+
139
+ Example::
140
+
141
+ rox = RoxUtils(project)
142
+ rmsver = rox.rmsversion('1.5')
143
+ print('The supported RMS version are {}'.format(rmsver))
144
+
145
+ """
146
+
147
+ return self._versions.get(apiversion, None)
148
+
149
+ def create_horizons_category(self, category, domain="depth", htype="surface"):
150
+ """Create one or more a Horizons category entries.
151
+
152
+ Args:
153
+ category (str or list): Name(s) of category to make, either as
154
+ a simple string or a list of strings.
155
+ domain (str): 'depth' (default) or 'time'
156
+ htype (str): Horizon type: surface/lines/points
157
+ """
158
+
159
+ _roxutils_etc.create_whatever_category(
160
+ self, category, stype="horizons", domain=domain, htype=htype
161
+ )
162
+
163
+ def create_zones_category(self, category, domain="thickness", htype="surface"):
164
+ """Create one or more a Horizons category entries.
165
+
166
+ Args:
167
+ category (str or list): Name(s) of category to make, either as
168
+ a simple string or a list of strings.
169
+ domain (str): 'thickness' (default) or ...?
170
+ htype (str): Horizon type: surface/lines/points
171
+ """
172
+
173
+ _roxutils_etc.create_whatever_category(
174
+ self, category, stype="zones", domain=domain, htype=htype
175
+ )
176
+
177
+ def delete_horizons_category(self, category):
178
+ """Delete on or more horizons or zones categories"""
179
+
180
+ _roxutils_etc.delete_whatever_category(self, category, stype="horizons")
181
+
182
+ def delete_zones_category(self, category):
183
+ """Delete on or more horizons or zones categories. See previous"""
184
+
185
+ _roxutils_etc.delete_whatever_category(self, category, stype="zones")
186
+
187
+ def clear_horizon_category(self, category):
188
+ """Clear (or make empty) the content of one or more horizon categories.
189
+
190
+ Args:
191
+ category (str or list): Name(s) of category to empty, either as
192
+ a simple string or a list of strings.
193
+
194
+ .. versionadded:: 2.1
195
+ """
196
+ _roxutils_etc.clear_whatever_category(self, category, stype="horizons")
197
+
198
+ def clear_zone_category(self, category):
199
+ """Clear (or make empty) the content of one or more zone categories.
200
+
201
+ Args:
202
+ category (str or list): Name(s) of category to empty, either as
203
+ a simple string or a list of strings.
204
+
205
+ .. versionadded:: 2.1
206
+ """
207
+ _roxutils_etc.clear_whatever_category(self, category, stype="zones")
@@ -0,0 +1,20 @@
1
+ """XTGeo surface package"""
2
+
3
+ from .regular_surface import (
4
+ RegularSurface,
5
+ surface_from_file,
6
+ surface_from_grid3d,
7
+ surface_from_rms,
8
+ surface_from_roxar,
9
+ )
10
+ from .surfaces import Surfaces, surfaces_from_grid
11
+
12
+ __all__ = [
13
+ "RegularSurface",
14
+ "surface_from_file",
15
+ "surface_from_rms",
16
+ "surface_from_roxar",
17
+ "surface_from_grid3d",
18
+ "Surfaces",
19
+ "surfaces_from_grid",
20
+ ]
@@ -0,0 +1,26 @@
1
+ import math
2
+
3
+ from xtgeo.xyz.points import points_from_surface
4
+ from xtgeo.xyz.polygons import Polygons
5
+
6
+
7
+ def create_boundary(self, alpha_factor, is_convex, simplify):
8
+ """Create boundary polygons for a surface."""
9
+
10
+ # make into points
11
+ points = points_from_surface(self)
12
+
13
+ # compute minimum alpha based on surface resolution
14
+ alpha = math.ceil(math.sqrt(self.xinc**2 + self.yinc**2) / 2)
15
+
16
+ pol = Polygons.boundary_from_points(points, alpha_factor, alpha, is_convex)
17
+
18
+ if simplify:
19
+ if isinstance(simplify, bool):
20
+ pol.simplify(tolerance=0.1)
21
+ elif isinstance(simplify, dict) and "tolerance" in simplify:
22
+ pol.simplify(**simplify)
23
+ else:
24
+ raise ValueError("Invalid values for simplify keyword")
25
+
26
+ return pol
@@ -0,0 +1,210 @@
1
+ """Regular surface vs Cube"""
2
+
3
+ import numpy as np
4
+
5
+ from xtgeo import _cxtgeo
6
+ from xtgeo.common.constants import UNDEF
7
+ from xtgeo.common.log import null_logger
8
+
9
+ logger = null_logger(__name__)
10
+
11
+
12
+ def slice_cube(
13
+ self,
14
+ cube,
15
+ scube,
16
+ zsurf=None,
17
+ sampling="nearest",
18
+ mask=True,
19
+ snapxy=False,
20
+ deadtraces=True,
21
+ algorithm=1,
22
+ ):
23
+ """Slicing a cube, using different algorithms"""
24
+
25
+ if algorithm == 2:
26
+ if snapxy:
27
+ return _slice_cube_v2(
28
+ self,
29
+ cube,
30
+ zsurf=zsurf,
31
+ sampling=sampling,
32
+ mask=mask,
33
+ deadtraces=deadtraces,
34
+ )
35
+ return _slice_cube_v2_resample(
36
+ self,
37
+ cube,
38
+ scube,
39
+ zsurf=zsurf,
40
+ sampling=sampling,
41
+ mask=mask,
42
+ deadtraces=deadtraces,
43
+ )
44
+
45
+ # legacy version:
46
+ return _slice_cube_v1(
47
+ self,
48
+ cube,
49
+ zsurf=zsurf,
50
+ sampling=sampling,
51
+ mask=mask,
52
+ snapxy=snapxy,
53
+ deadtraces=deadtraces,
54
+ )
55
+
56
+
57
+ def _slice_cube_v1(
58
+ self, cube, zsurf=None, sampling="nearest", mask=True, snapxy=False, deadtraces=True
59
+ ):
60
+ """
61
+ Private function for the Cube slicing. This is the legacy version up to version
62
+ 2.8.x but may remain default for a while
63
+ """
64
+
65
+ logger.info("Slice cube algorithm 1")
66
+ if zsurf is not None:
67
+ other = zsurf
68
+ else:
69
+ logger.info("The current surface is copied as 'other'")
70
+ other = self.copy()
71
+
72
+ if not self.compare_topology(other, strict=False):
73
+ raise RuntimeError("Topology of maps differ. Stop!")
74
+
75
+ opt2 = 0 if mask else 1
76
+
77
+ if deadtraces:
78
+ # set dead traces to cxtgeo UNDEF -> special treatment in the C code
79
+ olddead = cube.values_dead_traces(UNDEF)
80
+
81
+ cubeval1d = np.ravel(cube.values, order="C")
82
+
83
+ nsurf = self.ncol * self.nrow
84
+
85
+ usesampling = 0
86
+ if sampling == "trilinear":
87
+ usesampling = 1
88
+ if snapxy:
89
+ usesampling = 2
90
+
91
+ logger.debug("Running method from C... (using typemaps for numpies!:")
92
+ istat, v1d = _cxtgeo.surf_slice_cube(
93
+ cube.ncol,
94
+ cube.nrow,
95
+ cube.nlay,
96
+ cube.xori,
97
+ cube.xinc,
98
+ cube.yori,
99
+ cube.yinc,
100
+ cube.zori,
101
+ cube.zinc,
102
+ cube.rotation,
103
+ cube.yflip,
104
+ cubeval1d,
105
+ self.ncol,
106
+ self.nrow,
107
+ self.xori,
108
+ self.xinc,
109
+ self.yori,
110
+ self.yinc,
111
+ self.yflip,
112
+ self.rotation,
113
+ other.get_values1d(),
114
+ nsurf,
115
+ usesampling,
116
+ opt2,
117
+ )
118
+
119
+ self.set_values1d(v1d)
120
+
121
+ if deadtraces:
122
+ cube.values_dead_traces(olddead) # reset value for dead traces
123
+
124
+ return istat
125
+
126
+
127
+ def _slice_cube_v2(
128
+ self, cube, zsurf=None, sampling="nearest", mask=True, deadtraces=True
129
+ ):
130
+ """
131
+ This is the new version, optimised for the case where the surface has exact same
132
+ topology as the cube. This should both simplify and speed up calculations
133
+
134
+ From xtgeo 2.9
135
+ """
136
+
137
+ logger.info("Slice cube algorithm 2 with sampling %s", sampling)
138
+ other = zsurf if zsurf is not None else self.copy()
139
+
140
+ if not self.compare_topology(other, strict=False):
141
+ raise RuntimeError("Topology of maps differ. Stop!")
142
+
143
+ optmask = 0
144
+ if mask:
145
+ optmask = 1
146
+
147
+ if deadtraces:
148
+ # set dead traces to cxtgeo UNDEF -> special treatment in the C code
149
+ olddead = cube.values_dead_traces(UNDEF)
150
+
151
+ optnearest = 1
152
+ if sampling == "trilinear":
153
+ optnearest = 0
154
+
155
+ # cube and surf shall share same topology, e.g. cube.col == surf.ncol etc
156
+ # print(self.values.mask)
157
+ istat = _cxtgeo.surf_slice_cube_v3(
158
+ cube.ncol,
159
+ cube.nrow,
160
+ cube.nlay,
161
+ cube.zori,
162
+ cube.zinc,
163
+ cube.values,
164
+ other.values.data,
165
+ self.values.data,
166
+ self.values.mask,
167
+ optnearest,
168
+ optmask,
169
+ )
170
+
171
+ if istat != 0:
172
+ logger.warning("Problem, ISTAT = %s", istat)
173
+
174
+ if deadtraces:
175
+ cube.values_dead_traces(olddead) # reset value for dead traces
176
+
177
+ return istat
178
+
179
+
180
+ def _slice_cube_v2_resample(
181
+ self, cube, scube, zsurf=None, sampling="nearest", mask=True, deadtraces=True
182
+ ):
183
+ """Slicing with surfaces that not match the cube geometry, snapxy=False
184
+
185
+ The idea here is to resample the surface to the cube, then afterwards
186
+ do an inverse sampling
187
+ """
188
+ if self.compare_topology(scube, strict=False):
189
+ return _slice_cube_v2(self, cube, zsurf, sampling, mask, deadtraces)
190
+
191
+ scube.resample(self)
192
+
193
+ zcube = None
194
+ if zsurf:
195
+ zcube = scube.copy()
196
+ zcube.resample(zsurf)
197
+
198
+ istat = _slice_cube_v2(
199
+ scube,
200
+ cube=cube,
201
+ zsurf=zcube,
202
+ sampling=sampling,
203
+ mask=mask,
204
+ deadtraces=deadtraces,
205
+ )
206
+
207
+ # sample back
208
+ self.resample(scube, mask=mask)
209
+
210
+ return istat