pattern_sim.c 4.29 KB
Newer Older
1
2
3
4
5
/*
 * main.c
 *
 * (c) 2006-2009 Thomas White <thomas.white@desy.de>
 *
6
 * pattern_sim - Simulate diffraction patterns from small crystals
7
8
9
10
11
12
13
14
15
16
17
18
19
 *
 */


#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <stdarg.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
Thomas White's avatar
Thomas White committed
20
#include <getopt.h>
21

22
#include "image.h"
Thomas White's avatar
Thomas White committed
23
#include "diffraction.h"
24
#include "cell.h"
25
26
#include "utils.h"
#include "hdf5-file.h"
Thomas White's avatar
Thomas White committed
27
#include "detector.h"
28
29


Thomas White's avatar
Thomas White committed
30
static void show_help(const char *s)
31
{
Thomas White's avatar
Thomas White committed
32
33
	printf("Syntax: %s\n\n", s);
	printf("Simulate diffraction patterns from small crystals\n");
34
35
36
37
38
39
40
	printf(" probed with femosecond pulses from a free electron laser.\n\n");
	printf(" -h, --help                Display this help message\n");
	printf(" --simulation-details      Show details of the simulation\n");
	printf(" --near-bragg              Output h,k,l,I near Bragg conditions\n");
	printf(" -r, --random-orientation  Use a randomly generated orientation\n");
	printf("                            (a new orientation will be used for each image)\n");
	printf(" -n, --number=<N>          Generate N images.  Default 1\n");
Thomas White's avatar
Thomas White committed
41
42
43
}


44
static void show_details()
Thomas White's avatar
Thomas White committed
45
{
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
	printf("This program simulates diffraction patterns from small crystals illuminated\n");
	printf("with femtosecond X-ray pulses from a free electron laser.\n\n");
	printf("Scattering Factors\n");
	printf("------------------\n");
	printf("Scattering factors\n");
}


static struct quaternion read_quaternion()
{
	do {

		int r;
		float w, x, y, z;
		char line[1024];
		char *rval;

		printf("Please input quaternion: w x y z\n");
		rval = fgets(line, 1023, stdin);
		if ( rval == NULL ) return invalid_quaternion();
		chomp(line);

		r = sscanf(line, "%f %f %f %f", &w, &x, &y, &z);
		if ( r == 4 ) {

			struct quaternion quat;

			quat.w = w;
			quat.x = x;
			quat.y = y;
			quat.z = z;

			return quat;

		} else {
			fprintf(stderr, "Invalid rotation '%s'\n", line);
		}

	} while ( 1 );
85
86
87
88
89
}


int main(int argc, char *argv[])
{
90
	int c;
91
	struct image image;
92
	char filename[1024];
Thomas White's avatar
Thomas White committed
93
	int config_simdetails = 0;
94
95
96
97
98
	int config_nearbragg = 0;
	int config_randomquat = 0;
	int number = 1;  /* Index for the current image */
	int n_images = 1;  /* Generate one image by default */
	int done = 0;
Thomas White's avatar
Thomas White committed
99

100
	/* Long options */
Thomas White's avatar
Thomas White committed
101
	const struct option longopts[] = {
102
103
104
105
106
107
		{"help",               0, NULL,               'h'},
		{"simulation-details", 0, &config_simdetails,  1},
		{"near-bragg",         0, &config_nearbragg,   1},
		{"random-orientation", 0, NULL,               'r'},
		{"number",             1, NULL,               'n'},
		{0, 0, NULL, 0}
Thomas White's avatar
Thomas White committed
108
	};
109

110
111
	/* Short options */
	while ((c = getopt_long(argc, argv, "hrn:", longopts, NULL)) != -1) {
112

Thomas White's avatar
Thomas White committed
113
114
115
116
117
		switch (c) {
		case 'h' : {
			show_help(argv[0]);
			return 0;
		}
118

119
120
121
122
123
124
125
126
127
128
		case 'r' : {
			config_randomquat = 1;
			break;
		}

		case 'n' : {
			n_images = atoi(optarg);
			break;
		}

Thomas White's avatar
Thomas White committed
129
130
131
		case 0 : {
			break;
		}
132

Thomas White's avatar
Thomas White committed
133
134
135
		default : {
			return 1;
		}
136
137
138
139
		}

	}

Thomas White's avatar
Thomas White committed
140
	if ( config_simdetails ) {
141
		show_details();
Thomas White's avatar
Thomas White committed
142
143
144
		return 0;
	}

Thomas White's avatar
Thomas White committed
145
	/* Define image parameters */
Thomas White's avatar
Thomas White committed
146
147
	image.width = 1024;
	image.height = 1024;
Thomas White's avatar
Thomas White committed
148
	image.fmode = FORMULATION_CLEN;
Thomas White's avatar
Thomas White committed
149
150
	image.x_centre = 512.5;
	image.y_centre = 512.5;
Thomas White's avatar
Thomas White committed
151
	image.camera_len = 0.10;  /* 10 cm (front CCD can move from 5cm-20cm) */
Thomas White's avatar
Thomas White committed
152
	image.resolution = 13333.3; /* 75 micron pixel size */
Thomas White's avatar
Thomas White committed
153
154
155
156
157
158
159
	image.xray_energy = eV_to_J(2.0e3); /* 2 keV energy */
	image.lambda = ph_en_to_lambda(image.xray_energy);  /* Wavelength */
	image.molecule = NULL;

	/* Splurge a few useful numbers */
	printf("Wavelength is %f nm\n", image.lambda/1.0e-9);

160
161
	do {

162
163
164
		/* Read quaternion from stdin */
		if ( config_randomquat ) {
			image.orientation = random_quaternion();
165
		} else {
166
			image.orientation = read_quaternion();
167
168
		}

169
170
171
172
173
174
175
176
177
178
179
		if ( quaternion_valid(image.orientation) ) {
			fprintf(stderr, "Orientation modulus is not zero!\n");
			return 1;
		}

		/* Ensure no residual information */
		image.qvecs = NULL;
		image.sfacs = NULL;
		image.data = NULL;
		image.twotheta = NULL;
		image.hdr = NULL;
180

181
182
		get_diffraction(&image);
		record_image(&image);
Thomas White's avatar
Thomas White committed
183

184
185
		snprintf(filename, 1023, "results/sim-%i.h5", number);
		number++;
Thomas White's avatar
Thomas White committed
186

187
188
		/* Write the output file */
		hdf5_write(filename, image.data, image.width, image.height);
189

190
191
192
193
194
195
		/* Clean up */
		free(image.data);
		free(image.qvecs);
		free(image.hdr);
		free(image.sfacs);
		free(image.twotheta);
Thomas White's avatar
Thomas White committed
196

197
		if ( n_images && (number >= n_images) ) done = 1;
Thomas White's avatar
Thomas White committed
198

199
	} while ( !done );
200
201

	return 0;
202
}