
원자가 분자의 프로브 원자와 교차하는 방식을 모델링하기 위해 구 표면에 원호를 그리고 싶습니다. tikz 또는 점근선으로 그리고 싶은 예시 이미지를 첨부합니다.
도움을 주셔서 감사합니다.
답변1
다음 코드는 contour
모듈을 사용하여 매개변수화된 표면과 암시적으로 정의된 표면의 교차점을 계산합니다. Asymptote에서는 하나의 반투명 표면을 다른 표면 앞에 배치하는 것이 까다로울 수 있으므로 문제에 대한 완전한 솔루션을 제공하지 않습니다. 그러나 그것은 시작이고 적어도 제목의 질문에 어느 정도 대답합니다.
settings.outformat="png";
settings.render=4;
size(10cm);
import graph3;
import contour;
currentlight.background = black;
currentprojection = orthographic(5, 2, 4);
// Some aliases that make the contour module a bit easier to use.
typedef path[] disconnected_path;
typedef guide[] disconnected_guide;
typedef path3[] disconnected_path3;
real fuzz = .001;
real umax(surface s, real fuzz=fuzz) {
if (s.ucyclic()) return s.index.length;
else return s.index.length - fuzz;
}
real vmax(surface s, real fuzz=fuzz) {
if (s.vcyclic()) return s.index[0].length;
return s.index[0].length - fuzz;
}
int nu = 8, nv = 8;
path3 semicircle = Arc(c=O, -Z, Z, normal=X, n=nu);
surface myUnitsphere = surface(semicircle, c=O, axis=Z, n=nv);
surface sphere(triple c, real r) {
surface toReturn = shift(c)*scale3(r)*myUnitsphere;
return toReturn;
}
// Make the type function3 an alias f0r the type real(triple), i.e., a function3 is a function from triples to reals.
typedef real function3(triple);
// Make the type function2 an alias f0r the type real(real,real), i.e., a function2 is a function from (real, real) to reals.
typedef real function2(real, real);
// Returns the restriction of f to the surface s, given by its built-in parametrization.
function2 pullback(function3 f, surface s) {
return new real(real u, real v) {
return f(s.point(u,v));
};
}
/*
* Parameters: an implicit surface {f = 0} and a parametrized surface s.
* Returns a possibly disconnected path, in the coordinates of the parametric surface s, that describes
* the intersection of the two surfaces.
*/
disconnected_path parametrized_intersection(function3 f, surface s, pair smin = (0,0), pair smax = (umax(s), vmax(s))) {
disconnected_guide toReturn = contour(pullback(f, s), smin, smax, new real[] {0})[0];
return toReturn;
}
path3 on_surface(path p, surface s) {
int size = length(p);
triple[] points = new triple[size];
for (int i = 0; i < size; ++i) {
pair pathpoint = point(p,i);
points[i] = s.point(pathpoint.x, pathpoint.y);
}
path3 toReturn = operator..(...points);
if (cyclic(p)) {
toReturn = toReturn & cycle;
}
return toReturn;
}
disconnected_path3 on_surface(disconnected_path p, surface s) {
disconnected_path3 toReturn;
for (path segment : p) {
toReturn.push(on_surface(segment, s));
}
return toReturn;
}
function3 implicit_sphere(triple c, real r) {
return new real(triple p) {
return length(p - c)^2 - r^2;
};
}
/********************************/
surface mySphere = sphere(c=O, r=1);
draw(mySphere, surfacepen=material(diffusepen=gray(0.1), emissivepen=gray(0.9)));
triple c = 1.5Y;
real r = 0.8;
surface s = sphere(c=c, r=r);
function3 s_implicit = implicit_sphere(c=c, r=r);
disconnected_path param_circle = parametrized_intersection(s_implicit, mySphere);
disconnected_path3 circle = on_surface(param_circle, mySphere);
draw(s, surfacepen=material(diffusepen=0.5*blue + opacity(0.5), emissivepen=0.5*white));
draw(circle, blue);
c = 1.4X;
r = 0.5;
s = sphere(c=c, r=r);
s_implicit = implicit_sphere(c=c, r=r);
param_circle = parametrized_intersection(s_implicit, mySphere);
circle = on_surface(param_circle, mySphere);
draw(s, surfacepen=material(diffusepen=0.5*blue + opacity(0.5), emissivepen=0.5*white));
draw(circle, blue);
결과: