{"id":172469,"date":"2013-03-12T19:47:03","date_gmt":"2013-03-12T15:47:03","guid":{"rendered":"http:\/\/savepearlharbor.com\/?p=172469"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-29T21:00:00","slug":"","status":"publish","type":"post","link":"https:\/\/savepearlharbor.com\/?p=172469","title":{"rendered":"<span class=\"post_title\">\u0421\u044a\u0435\u043c\u043a\u0430 Time Lapse \u0432\u0438\u0434\u0435\u043e \u043f\u043e\u0434 Android<\/span>"},"content":{"rendered":"<div class=\"content html_format\"> \t\t\t<img decoding=\"async\" src=\"http:\/\/img-fotki.yandex.ru\/get\/6426\/77014867.0\/0_a8a5a_3fa2f2e7_L.jpeg\" alt=\"image\" align=\"right\"\/>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u043f\u0438\u0448\u0435\u043c \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0443 \u0434\u043b\u044f \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0441\u0432\u043e\u0438\u0445 \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0445 \u0444\u0438\u043b\u044c\u043c\u043e\u0432 \u0432 \u0442\u0435\u0445\u043d\u0438\u043a\u0435 <a href=\"http:\/\/en.wikipedia.org\/wiki\/Time-lapse_photography\">Time Lapse<\/a>. \u0417\u0430\u0432\u043e\u0440\u0430\u0436\u0438\u0432\u0430\u044e\u0449\u0435\u0435 \u0432\u0438\u0434\u0435\u043e, \u0441\u043d\u044f\u0442\u043e\u0435 \u0432 \u044d\u0442\u043e\u0439 \u0442\u0435\u0445\u043d\u0438\u043a\u0435 \u0441 \u0431\u043e\u0440\u0442\u0430 \u041c\u041a\u0421, \u043c\u043e\u0436\u043d\u043e \u043f\u043e\u0441\u043c\u043e\u0442\u0440\u0435\u0442\u044c <a href=\"http:\/\/www.youtube.com\/watch?v=Ip2ZGND1I9Q\">\u0437\u0434\u0435\u0441\u044c<\/a>, \u0431\u043e\u043b\u0435\u0435 \u0434\u043e\u0441\u0442\u0443\u043f\u043d\u044b\u0439 \u0432\u0430\u0440\u0438\u0430\u043d\u0442, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u043e\u0436\u043d\u043e \u043f\u043e\u0432\u0442\u043e\u0440\u0438\u0442\u044c \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043e\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u043c\u043e\u0439 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u044b \u2014 <a href=\"http:\/\/www.youtube.com\/watch?v=Tt-juyvIWMQ\">\u0437\u0434\u0435\u0441\u044c<\/a>.<\/p>\n<p>  \u041f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u0438\u043c\u0435\u0435\u0442 \u043f\u0440\u043e\u0441\u0442\u043e\u0439 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0438 \u043d\u0435\u0441\u043b\u043e\u0436\u043d\u044b\u0439 \u043f\u0440\u0438\u043d\u0446\u0438\u043f \u0440\u0430\u0431\u043e\u0442\u044b:<br \/>  \u2022\u00a0\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c \u0437\u0430\u0434\u0430\u0435\u0442 \u043f\u0435\u0440\u0438\u043e\u0434\u0438\u0447\u043d\u043e\u0441\u0442\u044c \u0441\u043d\u0438\u043c\u043a\u043e\u0432 \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u043d\u043e\u0439 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 (\u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, 10 \u0441) \u0438 \u0436\u0435\u043b\u0430\u0435\u043c\u0443\u044e \u0447\u0430\u0441\u0442\u043e\u0442\u0443 \u043a\u0430\u0434\u0440\u043e\u0432 \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c\u043e\u0433\u043e \u0432\u0438\u0434\u0435\u043e (\u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, 25 \u043a\u0430\u0434\u0440\u043e\u0432 \u0432 \u0441\u0435\u043a\u0443\u043d\u0434\u0443);<br \/>  \u2022\u00a0\u043f\u043e\u0441\u043b\u0435 \u043d\u0430\u0436\u0430\u0442\u0438\u044f \u043a\u043d\u043e\u043f\u043a\u0438 \u00ab\u0421\u0442\u0430\u0440\u0442\u00bb\u00a0 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u043a\u0430\u0436\u0434\u044b\u0435 10 \u0441\u0435\u043a\u0443\u043d\u0434 \u0434\u0435\u043b\u0430\u0435\u0442 \u0444\u043e\u0442\u043e\u0433\u0440\u0430\u0444\u0438\u044e \u0438 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442 jpg-\u0444\u0430\u0439\u043b \u043d\u0430 SD-\u043a\u0430\u0440\u0442\u0443;<br \/>  \u2022\u00a0\u043f\u0440\u043e\u0446\u0435\u0434\u0443\u0440\u0430 \u043f\u043e\u0432\u0442\u043e\u0440\u044f\u0435\u0442\u0441\u044f \u0434\u043e \u043d\u0430\u0436\u0430\u0442\u0438\u044f \u043a\u043d\u043e\u043f\u043a\u0438\u00a0\u00ab\u0421\u0442\u043e\u043f\u00bb \u0438 \u00ab\u0421\u043e\u0437\u0434\u0430\u0442\u044c \u0432\u0438\u0434\u0435\u043e\u00bb, \u043f\u043e\u0441\u043b\u0435 \u0447\u0435\u0433\u043e \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u0444\u043e\u0442\u043e\u0433\u0440\u0430\u0444\u0438\u0439 \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0430\u0435\u0442\u0441\u044f \u0432 \u0432\u0438\u0434\u0435\u043e \u0444\u0430\u0439\u043b \u0444\u043e\u0440\u043c\u0430\u0442\u0430 <a href=\"http:\/\/ru.wikipedia.org\/wiki\/MJPEG#.D0.9F.D1.80.D0.B5.D0.B8.D0.BC.D1.83.D1.89.D0.B5.D1.81.D1.82.D0.B2.D0.B0_.D0.B8_.D0.BD.D0.B5.D0.B4.D0.BE.D1.81.D1.82.D0.B0.D1.82.D0.BA.D0.B8\">Motion JPEG<\/a>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u043e\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043e\u0442\u0441\u043d\u044f\u0442\u044b\u0439 \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b \u0432 250 \u0440\u0430\u0437 (25 * 10) \u0431\u044b\u0441\u0442\u0440\u0435\u0435 \u0440\u0435\u0430\u043b\u044c\u043d\u043e\u0439 \u0441\u043a\u043e\u0440\u043e\u0441\u0442\u0438 \u043f\u0440\u043e\u0438\u0441\u0445\u043e\u0434\u0438\u0432\u0448\u0438\u0445 \u0441\u043e\u0431\u044b\u0442\u0438\u0439.<\/p>\n<p>  \u0412 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0435 \u0434\u0432\u0430 \u043e\u0441\u043d\u043e\u0432\u043d\u044b\u0445 \u043a\u043b\u0430\u0441\u0441\u0430\u00a0\u2014\u00a0<em>MainActivity<\/em>, \u0437\u0430\u043d\u0438\u043c\u0430\u044e\u0449\u0438\u0439\u0441\u044f \u0432\u0437\u0430\u0438\u043c\u043e\u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0435\u043c \u0441 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0438 \u043d\u0430\u043a\u043e\u043f\u043b\u0435\u043d\u0438\u0435\u043c \u0441\u043d\u0438\u043c\u043a\u043e\u0432 \u0438\u00a0<em>MJPEGGenerator<\/em>, \u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0439 \u0437\u0430 \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0435\u043d\u0438\u0435 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0438\u0437\u043e\u0431\u0440\u0430\u0436\u0435\u043d\u0438\u0439 \u0432 \u0432\u0438\u0434\u0435\u043e \u0444\u0430\u0439\u043b.<\/p>\n<p>  \u041a\u043b\u0430\u0441\u0441 <em>MJPEGGenerator<\/em>, \u0432\u0437\u044f\u0442\u044b\u0439 \u0441 <a href=\"https:\/\/code.google.com\/p\/javadrone\/source\/browse\/src\/com\/codeminders\/ardrone\/util\/MJPEGGenerator.java?r=7503a6e1ba48b78dc1d79d741ef8c01b524dac91\">code.google.com<\/a>, \u0431\u044b\u043b \u0441\u043b\u0435\u0433\u043a\u0430 \u043f\u0435\u0440\u0435\u0434\u0435\u043b\u0430\u043d \u0432 \u0441\u0432\u044f\u0437\u0438 \u0441 \u0442\u0435\u043c, \u0447\u0442\u043e \u0432 Android Java \u043e\u0442\u0441\u0443\u0442\u0441\u0442\u0432\u0443\u0435\u0442 \u043f\u0430\u043a\u0435\u0442 java.awt.<\/p>\n<p>  \u041f\u0440\u043e\u0446\u0435\u0434\u0443\u0440\u044b \u0440\u0430\u0431\u043e\u0442\u044b \u0441 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 \u0431\u044b\u043b\u0438 \u043f\u0440\u0435\u0438\u043c\u0443\u0449\u0435\u0441\u0442\u0432\u0435\u043d\u043d\u043e \u0432\u0437\u044f\u0442\u044b \u0438\u0437 \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b\u0430\u00a0<a href=\"http:\/\/habrahabr.ru\/post\/112272\/\">\u0420\u0430\u0431\u043e\u0442\u0430 \u0441 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 \u0432 Android<\/a>, \u0433\u0434\u0435 \u0435\u0441\u0442\u044c \u0445\u043e\u0440\u043e\u0448\u0435\u0435 \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435 \u043f\u0440\u0438\u043c\u0435\u043d\u0435\u043d\u043d\u044b\u0445 \u0440\u0435\u0448\u0435\u043d\u0438\u0439, \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0430 \u00ab\u0437\u0430\u043b\u0438\u043f\u0430\u043d\u0438\u0439\u00bb \u043a\u0430\u043c\u0435\u0440\u044b \u043f\u043e\u0441\u043b\u0435 \u043b\u043e\u043a\u0430\/\u0430\u043d\u043b\u043e\u043a\u0430 Android-\u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 \u0431\u044b\u043b\u0430 \u0443\u0441\u0442\u0440\u0430\u043d\u0435\u043d\u0430 \u0431\u043b\u0430\u0433\u043e\u0434\u0430\u0440\u044f\u00a0<a href=\"http:\/\/stackoverflow.com\/questions\/7186007\/camera-example-bug-when-locking-unlocking-device\">stackoverflow<\/a>.<\/p>\n<p>  \u041f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u0431\u044b\u043b\u0430 \u043e\u0442\u043b\u0430\u0436\u0435\u043d\u0430 \u043d\u0430 \u043f\u043b\u0430\u043d\u0448\u0435\u0442\u0435 Prestigio MultiPad 7.0 Prime \u043f\u043e\u0434 Android 4.0.<\/p>\n<p>  <a name=\"habracut\"><\/a><br \/>  <img decoding=\"async\" src=\"http:\/\/img-fotki.yandex.ru\/get\/5633\/77014867.0\/0_a8a5b_4429ac2d_L.png\" alt=\"image\" align=\"center\"\/><\/p>\n<p>  \u0420\u0430\u0441\u0441\u043c\u043e\u0442\u0440\u0438\u043c \u0431\u043e\u043b\u0435\u0435 \u043f\u043e\u0434\u0440\u043e\u0431\u043d\u043e \u0440\u0430\u0431\u043e\u0442\u0443 \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u044b\u0445 \u043a\u043e\u043c\u043f\u043e\u043d\u0435\u043d\u0442\u043e\u0432 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u044b, \u043d\u0435 \u043a\u0430\u0441\u0430\u044e\u0449\u0438\u0445\u0441\u044f \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u043e \u043a\u0430\u043c\u0435\u0440\u044b.<\/p>\n<p>  \u0414\u043b\u044f \u0442\u043e\u0433\u043e, \u0447\u0442\u043e\u0431\u044b \u044d\u043a\u0440\u0430\u043d \u0432\u043e \u0432\u0440\u0435\u043c\u044f \u0441\u044a\u0435\u043c\u043a\u0438 \u043d\u0435 \u0432\u044b\u043a\u043b\u044e\u0447\u0430\u043b\u0441\u044f, \u0431\u044b\u043b \u043f\u0440\u0438\u043c\u0435\u043d\u0435\u043d \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c\u00a0<em>PowerManager.WakeLock<\/em>:<\/p>\n<pre><code>private PowerManager.WakeLock wl;  public void onCreate(Bundle savedInstanceState) { ... PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE); wl = pm.newWakeLock(PowerManager.FULL_WAKE_LOCK, &quot;DoNotDimScreen&quot;); } <\/code><\/pre>\n<p>  \u041f\u0435\u0440\u0438\u043e\u0434\u0438\u0447\u043d\u043e\u0441\u0442\u044c \u0437\u0430\u043f\u0443\u0441\u043a\u0430 \u043a\u0430\u043c\u0435\u0440\u044b \u0440\u0435\u0433\u0443\u043b\u0438\u0440\u0443\u0435\u0442\u0441\u044f \u0442\u0430\u0439\u043c\u0435\u0440\u043e\u043c:<\/p>\n<pre><code>Timer updateTimer = new Timer(); ... updateTimer = new Timer(); updateTimer.scheduleAtFixedRate(new TimerTask() { public void run() { if ((camera != null) && (workMode == 1)) {\t\t\t\t\t\t\t\t\t\t\t\tcamera.takePicture(null, null, null, MainActivity.this); }} }, 0, capturePeriod * 1000); <\/code><\/pre>\n<p>  \u041f\u0435\u0440\u0435\u0434 \u043d\u0430\u0447\u0430\u043b\u043e\u043c \u0440\u0430\u0431\u043e\u0442\u044b \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u0442\u0441\u044f \u043d\u0430\u043b\u0438\u0447\u0438\u0435 SD-\u043a\u0430\u0440\u0442\u044b:<\/p>\n<pre><code>if (!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) Toast.makeText(MainActivity.this, &quot;Please mount SD card&quot;, Toast.LENGTH_LONG).show(); <\/code><\/pre>\n<p>  \u0414\u0430\u043d\u043d\u044b\u0435, \u0432\u0432\u0435\u0434\u0435\u043d\u043d\u044b\u0435 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c, \u043f\u0440\u043e\u0445\u043e\u0434\u044f\u0442 \u043f\u0440\u0435\u0434\u0432\u0430\u0440\u0438\u0442\u0435\u043b\u044c\u043d\u0443\u044e \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0443: \u0437\u0430\u043f\u044f\u0442\u044b\u0435, \u0432\u0432\u0435\u0434\u0435\u043d\u043d\u044b\u0435 \u0432 \u043a\u0430\u0447\u0435\u0441\u0442\u0432\u0435 \u0440\u0430\u0437\u0434\u0435\u043b\u0438\u0442\u0435\u043b\u044f \u0434\u0435\u0441\u044f\u0442\u0438\u0447\u043d\u044b\u0445 \u0440\u0430\u0437\u0440\u044f\u0434\u043e\u0432, \u0437\u0430\u043c\u0435\u043d\u044f\u044e\u0442\u0441\u044f \u043d\u0430 \u0442\u043e\u0447\u043a\u0443; \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u0435\u0442\u0441\u044f \u0432\u0432\u043e\u0434 \u043d\u0435 \u0446\u0438\u0444\u0440\u043e\u0432\u044b\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439; \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0432\u0432\u0435\u0434\u0435\u043d\u043d\u043e\u0433\u043e \u043f\u0435\u0440\u0438\u043e\u0434\u0430 \u0438 \u0447\u0430\u0441\u0442\u043e\u0442\u044b \u043a\u0430\u0434\u0440\u043e\u0432 \u043f\u0440\u043e\u0432\u0435\u0440\u044f\u044e\u0442\u0441\u044f \u043d\u0430 \u0432\u0445\u043e\u0436\u0434\u0435\u043d\u0438\u0435 \u0432 \u0434\u043e\u043f\u0443\u0441\u0442\u0438\u043c\u044b\u0439 \u0434\u0438\u0430\u043f\u0430\u0437\u043e\u043d:<\/p>\n<pre><code>periodEditText.addTextChangedListener(new TextWatcher() { public void afterTextChanged(Editable s) { if (periodEditText.getText().toString().length() == 0) capturePeriod = 0; else { if (isNum(periodEditText.getText().toString().replace(',', '.'))) { float a = Float.valueOf(periodEditText.getText().toString().replace(',', '.')); capturePeriod = (int) a; } else Toast.makeText(MainActivity.this, periodEditText.getText().toString() + &quot; - not a digit.&quot;, Toast.LENGTH_LONG).show(); }}  ...  if ((fps &lt; FPSMIN) || (fps &gt; FPSMAX)) Toast.makeText(MainActivity.this, &quot;FPS should be &quot; + FPSMIN + &quot; to &quot; + FPSMAX + &quot; frames per second&quot;, Toast.LENGTH_LONG).show(); <\/code><\/pre>\n<p>  \u0412 \u043d\u0430\u0447\u0430\u043b\u0435 \u0440\u0430\u0431\u043e\u0442\u044b \u0438\u0437 \u043f\u0430\u043f\u043a\u0438 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u044b \u0443\u0434\u0430\u043b\u044f\u044e\u0442\u0441\u044f \u0432\u0441\u0435 \u0444\u0430\u0439\u043b\u0430 *.jpg, \u043e\u0441\u0442\u0430\u0432\u0448\u0438\u0435\u0441\u044f \u043f\u043e\u0441\u043b\u0435 \u043f\u0440\u0435\u0434\u044b\u0434\u0443\u0449\u0435\u0433\u043e \u0441\u0435\u0430\u043d\u0441\u0430:<\/p>\n<pre><code>String sdPath = Environment.getExternalStorageDirectory().getPath() + &quot;\/TimeLapseFolder\/&quot;; File saveDir = new File(sdPath); if (saveDir.isDirectory()) { String[] children = saveDir.list(); for (int i = 0; i &lt; children.length; i++) { if (children[i].endsWith(&quot;.jpg&quot;)) new File(saveDir, children[i]).delete(); }} saveDir.delete(); <\/code><\/pre>\n<p>  \u041f\u043e\u0441\u043b\u0435 \u0441\u044a\u0435\u043c\u043a\u0438 \u043e\u0447\u0435\u0440\u0435\u0434\u043d\u043e\u0433\u043e \u043a\u0430\u0434\u0440\u0430 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044e \u043f\u043e\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u043e\u0441\u0442\u0430\u0432\u0448\u0435\u0435\u0441\u044f \u043d\u0430 \u043a\u0430\u0440\u0442\u0435 \u043c\u0435\u0441\u0442\u043e:<\/p>\n<pre><code>modeText.setText(&quot;Work mode: capturing, &quot; + String.valueOf(roundOneDecimal(megAvailable)) + &quot; Mbyte available on SD card&quot;); <\/code><\/pre>\n<p>  \u0421\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u043e \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u0432\u0438\u0434\u0435\u043e:<\/p>\n<pre><code>generator = new MJPEGGenerator(videofile, aviWidth, aviHeight, fps, lastPicture);  for (int addpic = 1; addpic &lt;= lastPicture; addpic++) { String numWithZeroes = intToString(addpic, 7); String curjpg = sdPath + numWithZeroes + &quot;.jpg&quot;; publishProgress(numWithZeroes); if (DEBUG) Log.v(TAG, &quot;Rendering jpg sdPath = &quot; + curjpg);  Bitmap bmp = BitmapFactory.decodeFile(curjpg); generator.addImage(bmp); } <\/code><\/pre>\n<p>  <em>MJPEGGenerator<\/em> \u0437\u0430\u043f\u0443\u0441\u043a\u0430\u0435\u0442\u0441\u044f \u0441\u043e \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0438\u043c\u0438 \u043f\u0430\u0440\u0430\u043c\u0435\u0442\u0440\u0430\u043c\u0438:<br \/>  videofile\u00a0\u2014 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u0435 \u0444\u0430\u0439\u043b\u0430 \u0432\u0438\u0434\u0435\u043e \u043a\u0430\u0436\u0434\u044b\u0439 \u0440\u0430\u0437 \u0431\u0435\u0440\u0435\u0442\u0441\u044f \u043d\u043e\u0432\u043e\u0435, \u043d\u0443\u043c\u0435\u0440\u0443\u0435\u043c\u043e\u0435 \u043f\u043e \u043c\u0430\u0441\u043a\u0435 TimeLapseMovieXXX.avi, \u0447\u0442\u043e\u0431\u044b \u0441\u043e\u0445\u0440\u0430\u043d\u0438\u0442\u044c \u0444\u0430\u0439\u043b\u044b, \u043e\u0442\u0441\u043d\u044f\u0442\u044b\u0435 \u0440\u0430\u043d\u0435\u0435;<br \/>  aviWidth, aviHeight\u00a0\u2014 \u0431\u0435\u0440\u0435\u0442\u0441\u044f \u0438\u0437 \u0441\u0432\u043e\u0439\u0441\u0442\u0432 \u043a\u0430\u043c\u0435\u0440\u044b;<br \/>  fps\u00a0\u2014 \u0437\u0430\u0434\u0430\u0435\u0442\u0441\u044f \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c;<br \/>  lastPicture\u00a0\u2014 \u043d\u043e\u043c\u0435\u0440 \u043f\u043e\u0441\u043b\u0435\u0434\u043d\u0435\u0439 \u0441\u043d\u044f\u0442\u043e\u0439 \u0444\u043e\u0442\u043e\u0433\u0440\u0430\u0444\u0438\u0438.<\/p>\n<p>  \u0427\u0442\u043e\u0431\u044b \u043d\u0435 \u043f\u043e\u0434\u0432\u0435\u0448\u0438\u0432\u0430\u0442\u044c \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0439 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441, \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u0432\u0438\u0434\u0435\u043e \u0437\u0430\u043f\u0443\u0441\u043a\u0430\u0435\u0442\u0441\u044f \u0432 \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u043e\u043c \u043f\u043e\u0442\u043e\u043a\u0435 <em>AsyncTask<\/em>, \u0432\u0437\u0430\u0438\u043c\u043e\u0434\u0435\u0439\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u043c \u0441 GUI \u0447\u0435\u0440\u0435\u0437\u00a0<em>onProgressUpdate<\/em>.<\/p>\n<p>  \u0421\u043e\u0434\u0435\u0440\u0436\u0438\u043c\u043e\u0435 \u043a\u043b\u044e\u0447\u0435\u0432\u044b\u0445 \u0444\u0430\u0439\u043b\u043e\u0432 \u043f\u043e\u043a\u0430\u0437\u0430\u043d\u043e \u043d\u0438\u0436\u0435, \u0430\u0440\u0445\u0438\u0432 \u043f\u0440\u043e\u0435\u043a\u0442\u0430 \u043c\u043e\u0436\u043d\u043e \u0441\u043a\u0430\u0447\u0430\u0442\u044c \u0441 <a href=\"http:\/\/sourceforge.net\/projects\/android-tlapse\/\">sourceforge.net<\/a>.<\/p>\n<div class=\"spoiler\"><b class=\"spoiler_title\">MainActivity.java<\/b><\/p>\n<div class=\"spoiler_text\">\n<pre><code>package com.sample.timelapse;  import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.text.DecimalFormat; import java.util.Arrays; import java.util.Timer; import java.util.TimerTask;  import android.annotation.SuppressLint; import android.app.Activity; import android.content.Context; import android.content.SharedPreferences; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.graphics.Color; import android.graphics.Point; import android.hardware.Camera; import android.hardware.Camera.Size; import android.os.AsyncTask; import android.os.Build; import android.os.Bundle; import android.os.Environment; import android.os.Handler; import android.os.PowerManager; import android.os.StatFs; import android.text.Editable; import android.text.TextWatcher; import android.util.Log; import android.util.TypedValue; import android.view.Display; import android.view.SurfaceHolder; import android.view.SurfaceView; import android.view.View; import android.view.View.OnFocusChangeListener; import android.view.ViewGroup.LayoutParams; import android.view.Window; import android.view.WindowManager; import android.view.inputmethod.InputMethodManager; import android.widget.Button; import android.widget.EditText; import android.widget.TextView; import android.widget.Toast;  public class MainActivity extends Activity implements SurfaceHolder.Callback, View.OnClickListener, Camera.PictureCallback, \t\tCamera.PreviewCallback { \tprivate MJPEGGenerator generator;  \tTimer updateTimer = new Timer(); \/\/ Main shoot timer  \tprivate static final int PERIODMIN = 2; \/\/ Seconds \tprivate static final int PERIODMAX = 1000; \/\/ Seconds  \tprivate static final int FPSMIN = 2; \tprivate static final int FPSMAX = 30;  \tint aviHeight = 0; \/\/ Dimensions of final video \tint aviWidth = 0;  \t\/\/ Work mode \t\/\/ 0: Ready to start \t\/\/ 1: Capturing photos \t\/\/ 2: Ready to create video \t\/\/ 3: Create video \tprivate int workMode = 0;  \tprivate int capturePeriod = 0; \tprivate int fps = 0;  \tprivate Camera camera; \tprivate SurfaceHolder surfaceHolder; \tprivate SurfaceView preview;  \tprivate static int LOGLEVEL = 2; \/\/ Set logging level \tprivate static boolean DEBUG = LOGLEVEL &gt; 1; \t@SuppressWarnings(&quot;unused&quot;) \tprivate static boolean WARNING = LOGLEVEL &gt; 0;  \tpublic static final String PREFS_NAME = &quot;MyPrefsFile&quot;; \/\/ For save and restore preferences  \tprivate static final String TAG = &quot;MainActivity&quot;; \/\/ Set logging tag  \tint lastPicture = 0; \/\/ Current picture counter \tint lastVideo = 0; \/\/ Current video file counter  \tint sWidth = 0; \/\/ Screen width \tint sHeight = 0; \/\/ Screen height \tint prevsWidth = 1; \/\/ Previous screen width (after previous onWindowFocusChanged) \tint prevsHeight = 1; \/\/ Previous screen height (after previous onWindowFocusChanged)  \tint commentTextBottom = 0; \tint oldLandCommentTextBottom = 0;  \tprivate TextView periodText; \tprivate TextView framerateText; \tprivate TextView totalsnapshotsText;  \tprivate Button startButton; \/\/ &quot;Start capture&quot; \tprivate Button createButton; \/\/ &quot;Create video&quot; \tint nativeButtonColor = 0;  \tprivate EditText periodEditText; \/\/ Period \tprivate TextView secondsText;  \tprivate EditText fpsEditText; \/\/ Frame rate \tprivate TextView fpsText;  \tprivate TextView modeText; \/\/ Show comments  \tfloat roundOneDecimal(float toround) { \t\tDecimalFormat twoDForm = new DecimalFormat(&quot;#.#&quot;); \t\treturn Float.valueOf(twoDForm.format(toround)); \t}  \tstatic String intToString(int num, int digits) { \t\tassert digits &gt; 0 : &quot;Invalid number of digits&quot;;  \t\tchar[] zeros = new char[digits]; \/\/ Create variable length array of zeros \t\tArrays.fill(zeros, '0');  \t\tDecimalFormat df = new DecimalFormat(String.valueOf(zeros)); \/\/ Format number as String  \t\treturn df.format(num); \t}  \tpublic boolean isNum(String s) { \t\ttry { \t\t\tDouble.parseDouble(s); \t\t} catch (NumberFormatException e) { \t\t\treturn false; \t\t} \t\treturn true; \t}  \tprivate PowerManager.WakeLock wl; \/\/ Stop screen from dimming by enforcing wake lock  \t@Override \tprotected void onPause() { \t\tsuper.onPause(); \/\/ onPause method in the parent class  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onPause&quot;);  \t\tsurfaceHolder.removeCallback(this); \t\tif (camera != null) { \t\t\tcamera.setPreviewCallback(null); \t\t\tcamera.stopPreview(); \t\t\tcamera.release(); \t\t\tcamera = null; \t\t}  \t\tpreview.setVisibility(View.GONE);  \t\twl.release(); \t}  \t@Override \tpublic void onCreate(Bundle savedInstanceState) { \t\tsuper.onCreate(savedInstanceState); \/\/ onCreate method in the parent class  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onCreate&quot;);  \t\trequestWindowFeature(Window.FEATURE_NO_TITLE); \/\/ App without a title \t\tgetWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN); \/\/ App without a status bar  \t\tsetContentView(R.layout.activity_main); \/\/ Set user interface  \t\tPowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE); \t\twl = pm.newWakeLock(PowerManager.FULL_WAKE_LOCK, &quot;DoNotDimScreen&quot;);  \t\tperiodText = (TextView) findViewById(R.id.periodText); \/\/ Text fields \t\tframerateText = (TextView) findViewById(R.id.framerateText); \t\ttotalsnapshotsText = (TextView) findViewById(R.id.totalsnapshotsText);  \t\tstartButton = (Button) findViewById(R.id.startButton); \/\/ Start capture button \t\tstartButton.setOnClickListener(this);  \t\tcreateButton = (Button) findViewById(R.id.createButton); \/\/ Create video button \t\tcreateButton.setOnClickListener(this); \t\tnativeButtonColor = createButton.getCurrentTextColor(); \t\tcreateButton.setTextColor(Color.GRAY);  \t\tperiodEditText = (EditText) findViewById(R.id.periodEditText); \/\/ Period \t\tsecondsText = (TextView) findViewById(R.id.secondsText);  \t\tperiodEditText.addTextChangedListener(new TextWatcher() { \t\t\tpublic void afterTextChanged(Editable s) { \t\t\t\tif (periodEditText.getText().toString().length() == 0) \t\t\t\t\tcapturePeriod = 0; \t\t\t\telse { \t\t\t\t\tif (isNum(periodEditText.getText().toString().replace(',', '.'))) { \t\t\t\t\t\tfloat a = Float.valueOf(periodEditText.getText().toString().replace(',', '.')); \t\t\t\t\t\tcapturePeriod = (int) a; \t\t\t\t\t} else \t\t\t\t\t\tToast.makeText(MainActivity.this, periodEditText.getText().toString() + &quot; - not a digit.&quot;, \t\t\t\t\t\t\t\tToast.LENGTH_LONG).show(); \t\t\t\t} \t\t\t}  \t\t\tpublic void beforeTextChanged(CharSequence s, int start, int count, int after) { \t\t\t}  \t\t\tpublic void onTextChanged(CharSequence s, int start, int before, int count) { \t\t\t} \t\t});  \t\tfpsEditText = (EditText) findViewById(R.id.fpsEditText); \/\/ fps EditText \t\tfpsText = (TextView) findViewById(R.id.fpsText);  \t\tfpsEditText.setOnFocusChangeListener(new OnFocusChangeListener() { \t\t\tpublic void onFocusChange(View v, boolean hasFocus) { \t\t\t\tif (!hasFocus) { \t\t\t\t\t\/\/ Hide soft keyboard after input \t\t\t\t\tInputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE); \t\t\t\t\timm.hideSoftInputFromWindow(fpsEditText.getWindowToken(), 0); \t\t\t\t} \t\t\t} \t\t});  \t\tfpsEditText.addTextChangedListener(new TextWatcher() { \t\t\tpublic void afterTextChanged(Editable s) { \t\t\t\tif (fpsEditText.getText().toString().length() == 0) \t\t\t\t\tfps = 0; \t\t\t\telse { \t\t\t\t\tif (isNum(fpsEditText.getText().toString().replace(',', '.'))) { \t\t\t\t\t\tfloat a = Float.valueOf(fpsEditText.getText().toString().replace(',', '.')); \t\t\t\t\t\tfps = (int) a; \t\t\t\t\t} else \t\t\t\t\t\tToast.makeText(MainActivity.this, fpsEditText.getText().toString() + &quot; - not a digit.&quot;, \t\t\t\t\t\t\t\tToast.LENGTH_LONG).show(); \t\t\t\t} \t\t\t}  \t\t\tpublic void beforeTextChanged(CharSequence s, int start, int count, int after) { \t\t\t}  \t\t\tpublic void onTextChanged(CharSequence s, int start, int before, int count) { \t\t\t} \t\t});  \t\tmodeText = (TextView) findViewById(R.id.modeText); \/\/ Show comments  \t\tSharedPreferences settings = getSharedPreferences(PREFS_NAME, 0); \/\/ Restore preferences \t\toldLandCommentTextBottom = settings.getInt(&quot;oldLandCommentTextBottom&quot;, 0); \t}  \t@Override \tprotected void onResume() { \t\tsuper.onResume(); \/\/ onResume method in the parent class  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onResume&quot;);  \t\tpreview = (SurfaceView) findViewById(R.id.mSurfaceView);  \t\tif (camera == null) { \t\t\tcamera = Camera.open(); \t\t\tcamera.startPreview(); \t\t}  \t\tsurfaceHolder = preview.getHolder(); \t\tsurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); \t\tsurfaceHolder.setSizeFromLayout(); \t\tsurfaceHolder.addCallback(this);  \t\tpreview.setVisibility(View.VISIBLE);  \t\twl.acquire();  \t\tSize previewSize = camera.getParameters().getPreviewSize(); \t\taviHeight = previewSize.height; \t\taviWidth = previewSize.width;  \t\tmodeText.setFocusableInTouchMode(true); \/\/ Set focus (and hide soft keyboard) \t\tmodeText.requestFocus(); \t}  \tpublic void surfaceChanged(SurfaceHolder holder, int format, int width, int height) { \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;surfaceChanged&quot;);  \t\ttry { \t\t\tcamera.setPreviewDisplay(surfaceHolder); \t\t} catch (IOException e) { \t\t\tToast.makeText(MainActivity.this, &quot;Error 1: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t} \t\tcamera.startPreview(); \t}  \tpublic void surfaceCreated(SurfaceHolder holder) { \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;surfaceCreated&quot;);  \t\ttry { \t\t\tcamera.setPreviewDisplay(holder); \t\t\tcamera.setPreviewCallback(this); \t\t} catch (IOException e) { \t\t\tToast.makeText(MainActivity.this, &quot;Error 2: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\tcamera.release(); \t\t\tcamera = null; \t\t}  \t\tSize previewSize = camera.getParameters().getPreviewSize(); \t\tfloat aspect = (float) previewSize.width \/ previewSize.height;  \t\tint previewSurfaceWidth = preview.getWidth();  \t\tLayoutParams lp = preview.getLayoutParams();  \t\t\/\/ \u0437\u0434\u0435\u0441\u044c \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u0438\u0440\u0443\u0435\u043c \u0440\u0430\u0437\u043c\u0435\u0440 \u043e\u0442\u043e\u0431\u0440\u0430\u0436\u0430\u0435\u043c\u043e\u0433\u043e preview \u0434\u043b\u044f \u043b\u0430\u043d\u0434\u0448\u0430\u0444\u0442\u043d\u043e\u0433\u043e \u0432\u0438\u0434\u0430, \u0447\u0442\u043e\u0431\u044b \u043d\u0435 \u0431\u044b\u043b\u043e \u0438\u0441\u043a\u0430\u0436\u0435\u043d\u0438\u0439 \t\t\/\/ camera.setDisplayOrientation(0); \t\tlp.width = previewSurfaceWidth; \t\tlp.height = (int) (previewSurfaceWidth \/ aspect);  \t\tpreview.setLayoutParams(lp); \t\tcamera.startPreview(); \t}  \tpublic void surfaceDestroyed(SurfaceHolder holder) { \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;surfaceDestroyed&quot;); \t}  \t@SuppressLint(&quot;NewApi&quot;) \t@SuppressWarnings(&quot;deprecation&quot;) \tvoid getDisplaySize() { \t\ttry { \t\t\tif (Build.VERSION.SDK_INT &gt;= 13) { \t\t\t\tDisplay display = getWindowManager().getDefaultDisplay(); \t\t\t\tPoint size = new Point(); \t\t\t\tdisplay.getSize(size); \t\t\t\tsWidth = size.x; \t\t\t\tsHeight = size.y; \t\t\t} else { \t\t\t\tDisplay display = getWindowManager().getDefaultDisplay(); \t\t\t\tsWidth = display.getWidth(); \t\t\t\tsHeight = display.getHeight(); \t\t\t} \t\t} catch (Exception e) { \t\t\tToast.makeText(MainActivity.this, &quot;Error 3: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t} \t}  \t@Override \tpublic void onWindowFocusChanged(boolean hasFocus) { \t\tsuper.onWindowFocusChanged(hasFocus); \t\tif (hasFocus) { \t\t\tgetDisplaySize();  \t\t\tif ((prevsWidth != sWidth) || (prevsHeight != sHeight)) { \/\/ If orientation changed \t\t\t\tcommentTextBottom = modeText.getTop() + modeText.getHeight(); \/\/ Calculate magnification factor  \t\t\t\tfloat heightRatio = 0;  \t\t\t\t\/\/ Landscape \t\t\t\theightRatio = (float) sHeight \/ (float) commentTextBottom; \t\t\t\toldLandCommentTextBottom = commentTextBottom;  \t\t\t\tif (heightRatio &gt; 1) \t\t\t\t\theightRatio = 0.7f * heightRatio; \t\t\t\telse \t\t\t\t\theightRatio = heightRatio \/ 0.7f;  \t\t\t\t\/\/ Adjust fonts \t\t\t\tperiodText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * periodText.getTextSize()); \t\t\t\tperiodEditText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * periodEditText.getTextSize()); \t\t\t\tsecondsText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * secondsText.getTextSize()); \t\t\t\tframerateText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * framerateText.getTextSize()); \t\t\t\tfpsEditText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * fpsEditText.getTextSize()); \t\t\t\tfpsText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * fpsText.getTextSize()); \t\t\t\ttotalsnapshotsText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * totalsnapshotsText.getTextSize()); \t\t\t\tmodeText.setTextSize(TypedValue.COMPLEX_UNIT_PX, heightRatio * modeText.getTextSize());  \t\t\t\t\/\/ Some components have text size a little less \t\t\t\tstartButton.setTextSize(TypedValue.COMPLEX_UNIT_PX, 0.8f * heightRatio * startButton.getTextSize()); \t\t\t\tcreateButton.setTextSize(TypedValue.COMPLEX_UNIT_PX, 0.8f * heightRatio * createButton.getTextSize());  \t\t\t\t\/\/ If user comment string not formed \t\t\t\tif (modeText.getText().equals(getResources().getString(R.string.longestComment))) \t\t\t\t\tmodeText.setText(getString(R.string.modeText)); \t\t\t} \t\t\tprevsWidth = sWidth; \t\t\tprevsHeight = sHeight; \t\t} \t}  \tpublic void onClick(View v) { \t\tif (v == startButton) { \t\t\tif (workMode == 0) { \t\t\t\tif (!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) \t\t\t\t\tToast.makeText(MainActivity.this, &quot;Please mount SD card&quot;, Toast.LENGTH_LONG).show(); \t\t\t\telse if ((capturePeriod &lt; PERIODMIN) || (capturePeriod &gt; PERIODMAX)) \t\t\t\t\tToast.makeText(MainActivity.this, \t\t\t\t\t\t\t&quot;Snapshots period should be &quot; + PERIODMIN + &quot; to &quot; + PERIODMAX + &quot; seconds&quot;, Toast.LENGTH_LONG) \t\t\t\t\t\t\t.show(); \t\t\t\telse if ((fps &lt; FPSMIN) || (fps &gt; FPSMAX)) \t\t\t\t\tToast.makeText(MainActivity.this, &quot;FPS should be &quot; + FPSMIN + &quot; to &quot; + FPSMAX + &quot; frames per second&quot;, \t\t\t\t\t\t\tToast.LENGTH_LONG).show(); \t\t\t\telse { \t\t\t\t\tif (updateTimer != null) \t\t\t\t\t\tupdateTimer.cancel();  \t\t\t\t\ttry { \t\t\t\t\t\tupdateTimer = new Timer();  \t\t\t\t\t\tupdateTimer.scheduleAtFixedRate(new TimerTask() { \t\t\t\t\t\t\tpublic void run() { \t\t\t\t\t\t\t\tif ((camera != null) && (workMode == 1)) { \t\t\t\t\t\t\t\t\tcamera.takePicture(null, null, null, MainActivity.this); \t\t\t\t\t\t\t\t} \t\t\t\t\t\t\t} \t\t\t\t\t\t}, 0, capturePeriod * 1000); \t\t\t\t\t} catch (Exception e) { \t\t\t\t\t\tToast.makeText(MainActivity.this, &quot;Error 4: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\t\t\t}  \t\t\t\t\t\/\/ Delete all jpg's \t\t\t\t\ttry { \t\t\t\t\t\tString sdPath = Environment.getExternalStorageDirectory().getPath() + &quot;\/TimeLapseFolder\/&quot;; \t\t\t\t\t\tif (DEBUG) \t\t\t\t\t\t\tLog.v(TAG, &quot;Delete jpg's sdPath = &quot; + sdPath);  \t\t\t\t\t\tFile saveDir = new File(sdPath);  \t\t\t\t\t\tif (saveDir.isDirectory()) { \t\t\t\t\t\t\tString[] children = saveDir.list(); \t\t\t\t\t\t\tfor (int i = 0; i &lt; children.length; i++) { \t\t\t\t\t\t\t\tif (children[i].endsWith(&quot;.jpg&quot;)) \t\t\t\t\t\t\t\t\tnew File(saveDir, children[i]).delete(); \t\t\t\t\t\t\t} \t\t\t\t\t\t} \t\t\t\t\t\tsaveDir.delete(); \t\t\t\t\t} catch (Exception e) { \t\t\t\t\t\tToast.makeText(MainActivity.this, &quot;Error 5: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\t\t\t}  \t\t\t\t\tlastPicture = 0; \t\t\t\t\tworkMode = 1; \t\t\t\t\tstartButton.setText(&quot;Stop capture&quot;); \t\t\t\t\tmodeText.setText(&quot;Work mode: capturing&quot;); \t\t\t\t\ttotalsnapshotsText.setText(&quot;Total snapshots: &quot; + String.valueOf(lastPicture)); \t\t\t\t} \t\t\t} else if (workMode == 1) { \t\t\t\tworkMode = 2; \t\t\t\tcreateButton.setTextColor(nativeButtonColor); \t\t\t\tstartButton.setText(&quot;Start capture&quot;); \t\t\t\tstartButton.setTextColor(Color.GRAY); \t\t\t\tmodeText.setText(&quot;Work mode: ready to start&quot;); \t\t\t} \t\t}  \t\tif (v == createButton) { \t\t\tif (workMode == 2) { \t\t\t\tif (!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) \t\t\t\t\tToast.makeText(MainActivity.this, &quot;Please mount SD card&quot;, Toast.LENGTH_LONG).show(); \t\t\t\telse if ((capturePeriod &lt; PERIODMIN) || (capturePeriod &gt; PERIODMAX)) \t\t\t\t\tToast.makeText(MainActivity.this, \t\t\t\t\t\t\t&quot;Snapshots period should be &quot; + PERIODMIN + &quot; to &quot; + PERIODMAX + &quot; seconds&quot;, Toast.LENGTH_LONG) \t\t\t\t\t\t\t.show(); \t\t\t\telse if ((fps &lt; FPSMIN) || (fps &gt; FPSMAX)) \t\t\t\t\tToast.makeText(MainActivity.this, &quot;FPS should be &quot; + FPSMIN + &quot; to &quot; + FPSMAX + &quot; frames per second&quot;, \t\t\t\t\t\t\tToast.LENGTH_LONG).show(); \t\t\t\telse { \t\t\t\t\tworkMode = 3; \t\t\t\t\tcreateButton.setTextColor(Color.GRAY); \t\t\t\t\tstartButton.setTextColor(Color.GRAY); \t\t\t\t\tmodeText.setText(&quot;Work mode: create video file, please wait&quot;); \t\t\t\t\tnew CreateMovieInBackground().execute(); \t\t\t\t} \t\t\t} \t\t} \t}  \t@Override \tprotected void onSaveInstanceState(Bundle outState) { \t\tsuper.onSaveInstanceState(outState); \/\/ onSaveInstanceState method in the parent class  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onSaveInstanceState&quot;);  \t\tSharedPreferences settings = getSharedPreferences(PREFS_NAME, 0); \t\tSharedPreferences.Editor editor = settings.edit(); \t\teditor.putInt(&quot;oldLandCommentTextBottom&quot;, oldLandCommentTextBottom); \t\teditor.commit(); \t}  \t@Override \tprotected void onRestoreInstanceState(Bundle savedInstanceState) { \t\tsuper.onRestoreInstanceState(savedInstanceState); \/\/ onRestoreInstanceState method in the parent class  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onRestoreInstanceState&quot;); \t}  \tpublic void onPictureTaken(byte[] paramArrayOfByte, Camera paramCamera) { \t\tnew SaveInBackground().execute(paramArrayOfByte);  \t\tif (DEBUG) \t\t\tLog.v(TAG, &quot;onPictureTaken&quot;);  \t\t\/\/ \u043f\u043e\u0441\u043b\u0435 \u0442\u043e\u0433\u043e, \u043a\u0430\u043a \u0441\u043d\u0438\u043c\u043e\u043a \u0441\u0434\u0435\u043b\u0430\u043d, \u043f\u043e\u043a\u0430\u0437 \u043f\u0440\u0435\u0432\u044c\u044e \u043e\u0442\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f. \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0432\u043a\u043b\u044e\u0447\u0438\u0442\u044c \u0435\u0433\u043e \t\tparamCamera.startPreview();  \t\ttotalsnapshotsText.setText(&quot;Total snapshots: &quot; + String.valueOf(lastPicture));  \t\tStatFs stat = new StatFs(Environment.getExternalStorageDirectory().getPath());  \t\tlong bytesAvailable = (long) stat.getBlockSize() * (long) stat.getAvailableBlocks(); \t\tfloat megAvailable = bytesAvailable \/ (1024.f * 1024.f);  \t\tmodeText.setText(&quot;Work mode: capturing, &quot; + String.valueOf(roundOneDecimal(megAvailable)) \t\t\t\t+ &quot; Mbyte available on SD card&quot;); \t}  \tclass SaveInBackground extends AsyncTask&lt;byte[], String, String&gt; { \t\t@Override \t\tprotected String doInBackground(byte[]... arrayOfByte) { \t\t\ttry { \t\t\t\tString sdPath = Environment.getExternalStorageDirectory().getPath() + &quot;\/TimeLapseFolder\/&quot;; \t\t\t\tFile saveDir = new File(sdPath);  \t\t\t\tif (!saveDir.exists()) \t\t\t\t\tsaveDir.mkdirs();  \t\t\t\tlastPicture++;  \t\t\t\tString numWithZeroes = intToString(lastPicture, 7); \t\t\t\tString curjpg = sdPath + numWithZeroes + &quot;.jpg&quot;;  \t\t\t\tif (DEBUG) \t\t\t\t\tLog.v(TAG, &quot;Save jpg sdPath = &quot; + curjpg);  \t\t\t\tFileOutputStream os = new FileOutputStream(curjpg); \t\t\t\tos.write(arrayOfByte[0]); \t\t\t\tos.close(); \t\t\t} catch (Exception e) { \t\t\t\tToast.makeText(MainActivity.this, &quot;Error 6: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\t} \t\t\treturn (null); \t\t} \t}  \tclass CreateMovieInBackground extends AsyncTask&lt;byte[], String, String&gt; {  \t\tprotected void onProgressUpdate(String... values) { \t\t\tmodeText.setText(&quot;Work mode: rendering &quot; + values[0] + &quot;.jpg&quot;); \t\t}  \t\tprotected void onPostExecute(String result) { \t\t\tworkMode = 0; \t\t\ttotalsnapshotsText.setText(&quot;Total snapshots: 0&quot;); \t\t\tlastPicture = 0;  \t\t\tString sdPath = Environment.getExternalStorageDirectory().getPath() + &quot;\/TimeLapseFolder\/&quot;;  \t\t\tmodeText.setText(&quot;Work mode:&quot; + sdPath + &quot;TimeLapseMovie&quot; + intToString(lastVideo, 3) + &quot;.avi is rendered&quot;); \t\t\tHandler handler = new Handler(); \t\t\thandler.postDelayed(new Runnable() { \t\t\t\tpublic void run() { \t\t\t\t\tmodeText.setText(&quot;Work mode: ready to start&quot;); \t\t\t\t\tstartButton.setTextColor(nativeButtonColor); \t\t\t\t} \t\t\t}, 5000); \t\t}  \t\t@Override \t\tprotected String doInBackground(byte[]... arrayOfByte) { \t\t\ttry {  \t\t\t\tFile videofile = null;  \t\t\t\tString sdPath = Environment.getExternalStorageDirectory().getPath() + &quot;\/TimeLapseFolder\/&quot;;  \t\t\t\t\/\/ Choosing a name for the file \t\t\t\tdo { \t\t\t\t\tlastVideo++; \t\t\t\t\tString curavi = sdPath + &quot;TimeLapseMovie&quot; + intToString(lastVideo, 3) + &quot;.avi&quot;;  \t\t\t\t\tif (DEBUG) \t\t\t\t\t\tLog.v(TAG, &quot;AVI name = &quot; + curavi);  \t\t\t\t\tvideofile = new File(curavi); \t\t\t\t} while (videofile.exists());  \t\t\t\tgenerator = new MJPEGGenerator(videofile, aviWidth, aviHeight, fps, lastPicture);  \t\t\t\tfor (int addpic = 1; addpic &lt;= lastPicture; addpic++) { \t\t\t\t\tString numWithZeroes = intToString(addpic, 7); \t\t\t\t\tString curjpg = sdPath + numWithZeroes + &quot;.jpg&quot;;  \t\t\t\t\tpublishProgress(numWithZeroes);  \t\t\t\t\tif (DEBUG) \t\t\t\t\t\tLog.v(TAG, &quot;Rendering jpg sdPath = &quot; + curjpg);  \t\t\t\t\tBitmap bmp = BitmapFactory.decodeFile(curjpg); \t\t\t\t\tgenerator.addImage(bmp); \t\t\t\t}  \t\t\t\t\/\/ Delete all jpg's \t\t\t\ttry { \t\t\t\t\tif (DEBUG) \t\t\t\t\t\tLog.v(TAG, &quot;Delete jpg's sdPath = &quot; + sdPath);  \t\t\t\t\tFile saveDir = new File(sdPath);  \t\t\t\t\tif (saveDir.isDirectory()) { \t\t\t\t\t\tString[] children = saveDir.list(); \t\t\t\t\t\tfor (int i = 0; i &lt; children.length; i++) { \t\t\t\t\t\t\tif (children[i].endsWith(&quot;.jpg&quot;)) \t\t\t\t\t\t\t\tnew File(saveDir, children[i]).delete(); \t\t\t\t\t\t} \t\t\t\t\t} \t\t\t\t\tsaveDir.delete(); \t\t\t\t} catch (Exception e) { \t\t\t\t\tToast.makeText(MainActivity.this, &quot;Error 7: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\t\t}  \t\t\t\tgenerator.finishAVI();  \t\t\t} catch (Exception e) { \t\t\t\tToast.makeText(MainActivity.this, &quot;Error 8: &quot; + e.toString(), Toast.LENGTH_LONG).show(); \t\t\t} \t\t\treturn &quot;OK&quot;; \t\t} \t}  \tpublic void onPreviewFrame(byte[] paramArrayOfByte, Camera paramCamera) { \t} } <\/code><\/pre>\n<p>  <\/div>\n<\/div>\n<div class=\"spoiler\"><b class=\"spoiler_title\">MJPEGGenerator.java<\/b><\/p>\n<div class=\"spoiler_text\">\n<pre><code>package com.sample.timelapse;   \/\/  \/\/ MJPEGGenerator.java  \/\/  \/\/ Created on April 17, 2006, 11:48 PM  \/\/  \/\/ To change this template, choose Tools | Options and locate the template under  \/\/ the Source Creation and Management node. Right-click the template and choose  \/\/ Open. You can then make changes to the template in the Source Editor.  \/\/  import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileOutputStream; import java.io.RandomAccessFile; import java.nio.channels.FileChannel; import java.util.ArrayList; import java.util.Arrays; import java.util.List;  import android.graphics.Bitmap;   \/\/  \/\/  \/\/ @author monceaux  \/\/ public class MJPEGGenerator { \t\/\/ \t\/\/ Info needed for MJPEG AVI \t\/\/ \t\/\/ - size of file minus &quot;RIFF & 4 byte file size&quot; \t\/\/  \tint width = 0; \tint height = 0; \tdouble framerate = 0; \tint numFrames = 0; \tFile aviFile = null; \tFileOutputStream aviOutput = null; \tFileChannel aviChannel = null;  \tlong riffOffset = 0; \tlong aviMovieOffset = 0;  \tAVIIndexList indexlist = null;  \t\/\/ Creates a new instance of MJPEGGenerator \tpublic MJPEGGenerator(File aviFile, int width, int height, double framerate, int numFrames) throws Exception { \t\tthis.aviFile = aviFile; \t\tthis.width = width; \t\tthis.height = height; \t\tthis.framerate = framerate; \t\tthis.numFrames = numFrames; \t\taviOutput = new FileOutputStream(aviFile); \t\taviChannel = aviOutput.getChannel();  \t\tRIFFHeader rh = new RIFFHeader(); \t\taviOutput.write(rh.toBytes()); \t\taviOutput.write(new AVIMainHeader().toBytes()); \t\taviOutput.write(new AVIStreamList().toBytes()); \t\taviOutput.write(new AVIStreamHeader().toBytes()); \t\taviOutput.write(new AVIStreamFormat().toBytes()); \t\taviOutput.write(new AVIJunk().toBytes()); \t\taviMovieOffset = aviChannel.position(); \t\taviOutput.write(new AVIMovieList().toBytes()); \t\tindexlist = new AVIIndexList(); \t}  \tpublic void addImage(Bitmap image) throws Exception { \t\tbyte[] fcc = new byte[] { '0', '0', 'd', 'b' }; \t\tbyte[] imagedata = writeImageToBytes(image); \t\tint useLength = imagedata.length; \t\tlong position = aviChannel.position(); \t\tint extra = (useLength + (int) position) % 4; \t\tif (extra &gt; 0) \t\t\tuseLength = useLength + extra;  \t\tindexlist.addAVIIndex((int) position, useLength);  \t\taviOutput.write(fcc); \t\taviOutput.write(intBytes(swapInt(useLength))); \t\taviOutput.write(imagedata); \t\tif (extra &gt; 0) { \t\t\tfor (int i = 0; i &lt; extra; i++) \t\t\t\taviOutput.write(0); \t\t} \t\timagedata = null; \t} \tpublic void finishAVI() throws Exception { \t\tbyte[] indexlistBytes = indexlist.toBytes(); \t\taviOutput.write(indexlistBytes); \t\taviOutput.close(); \t\tlong size = aviFile.length(); \t\tRandomAccessFile raf = new RandomAccessFile(aviFile, &quot;rw&quot;); \t\traf.seek(4); \t\traf.write(intBytes(swapInt((int) size - 8))); \t\traf.seek(aviMovieOffset + 4); \t\traf.write(intBytes(swapInt((int) (size - 8 - aviMovieOffset - indexlistBytes.length)))); \t\traf.close(); \t} \tpublic static int swapInt(int v) { \t\treturn (v &gt;&gt;&gt; 24) | (v &lt;&lt; 24) | ((v &lt;&lt; 8) & 0x00FF0000) | ((v &gt;&gt; 8) & 0x0000FF00); \t}  \tpublic static short swapShort(short v) { \t\treturn (short) ((v &gt;&gt;&gt; 8) | (v &lt;&lt; 8)); \t} \tpublic static byte[] intBytes(int i) { \t\tbyte[] b = new byte[4]; \t\tb[0] = (byte) (i &gt;&gt;&gt; 24); \t\tb[1] = (byte) ((i &gt;&gt;&gt; 16) & 0x000000FF); \t\tb[2] = (byte) ((i &gt;&gt;&gt; 8) & 0x000000FF); \t\tb[3] = (byte) (i & 0x000000FF);  \t\treturn b; \t}  \tpublic static byte[] shortBytes(short i) { \t\tbyte[] b = new byte[2]; \t\tb[0] = (byte) (i &gt;&gt;&gt; 8); \t\tb[1] = (byte) (i & 0x000000FF);  \t\treturn b; \t}  \tprivate class RIFFHeader { \t\tpublic byte[] fcc = new byte[] { 'R', 'I', 'F', 'F' }; \t\tpublic int fileSize = 0; \t\tpublic byte[] fcc2 = new byte[] { 'A', 'V', 'I', ' ' }; \t\tpublic byte[] fcc3 = new byte[] { 'L', 'I', 'S', 'T' }; \t\tpublic int listSize = 200; \t\tpublic byte[] fcc4 = new byte[] { 'h', 'd', 'r', 'l' };  \t\tpublic RIFFHeader() {  \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(fileSize))); \t\t\tbaos.write(fcc2); \t\t\tbaos.write(fcc3); \t\t\tbaos.write(intBytes(swapInt(listSize))); \t\t\tbaos.write(fcc4); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIMainHeader { \t\t\/\/ \t\t\/\/ \t\t\/\/ FOURCC fcc; DWORD cb; DWORD dwMicroSecPerFrame; DWORD dwMaxBytesPerSec; DWORD dwPaddingGranularity; DWORD \t\t\/\/ dwFlags; DWORD dwTotalFrames; DWORD dwInitialFrames; DWORD dwStreams; DWORD dwSuggestedBufferSize; DWORD \t\t\/\/ dwWidth; DWORD dwHeight; DWORD dwReserved[4]; \t\t\/\/  \t\tpublic byte[] fcc = new byte[] { 'a', 'v', 'i', 'h' }; \t\tpublic int cb = 56; \t\tpublic int dwMicroSecPerFrame = 0; \/\/ (1 \t\t\t\t\t\t\t\t\t\t\t\/\/ \/ \t\t\t\t\t\t\t\t\t\t\t\/\/ frames \t\t\t\t\t\t\t\t\t\t\t\/\/ per \t\t\t\t\t\t\t\t\t\t\t\/\/ sec) \t\t\t\t\t\t\t\t\t\t\t\/\/ * \t\t\t\t\t\t\t\t\t\t\t\/\/ 1,000,000 \t\tpublic int dwMaxBytesPerSec = 10000000; \t\tpublic int dwPaddingGranularity = 0; \t\tpublic int dwFlags = 65552; \t\tpublic int dwTotalFrames = 0; \/\/ replace \t\t\t\t\t\t\t\t\t\t\/\/ with \t\t\t\t\t\t\t\t\t\t\/\/ correct \t\t\t\t\t\t\t\t\t\t\/\/ value \t\tpublic int dwInitialFrames = 0; \t\tpublic int dwStreams = 1; \t\tpublic int dwSuggestedBufferSize = 0; \t\tpublic int dwWidth = 0; \/\/ replace \t\t\t\t\t\t\t\t\/\/ with \t\t\t\t\t\t\t\t\/\/ correct \t\t\t\t\t\t\t\t\/\/ value \t\tpublic int dwHeight = 0; \/\/ replace \t\t\t\t\t\t\t\t\t\/\/ with \t\t\t\t\t\t\t\t\t\/\/ correct \t\t\t\t\t\t\t\t\t\/\/ value \t\tpublic int[] dwReserved = new int[4];  \t\tpublic AVIMainHeader() { \t\t\tdwMicroSecPerFrame = (int) ((1.0 \/ framerate) * 1000000.0); \t\t\tdwWidth = width; \t\t\tdwHeight = height; \t\t\tdwTotalFrames = numFrames; \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(cb))); \t\t\tbaos.write(intBytes(swapInt(dwMicroSecPerFrame))); \t\t\tbaos.write(intBytes(swapInt(dwMaxBytesPerSec))); \t\t\tbaos.write(intBytes(swapInt(dwPaddingGranularity))); \t\t\tbaos.write(intBytes(swapInt(dwFlags))); \t\t\tbaos.write(intBytes(swapInt(dwTotalFrames))); \t\t\tbaos.write(intBytes(swapInt(dwInitialFrames))); \t\t\tbaos.write(intBytes(swapInt(dwStreams))); \t\t\tbaos.write(intBytes(swapInt(dwSuggestedBufferSize))); \t\t\tbaos.write(intBytes(swapInt(dwWidth))); \t\t\tbaos.write(intBytes(swapInt(dwHeight))); \t\t\tbaos.write(intBytes(swapInt(dwReserved[0]))); \t\t\tbaos.write(intBytes(swapInt(dwReserved[1]))); \t\t\tbaos.write(intBytes(swapInt(dwReserved[2]))); \t\t\tbaos.write(intBytes(swapInt(dwReserved[3]))); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIStreamList { \t\tpublic byte[] fcc = new byte[] { 'L', 'I', 'S', 'T' }; \t\tpublic int size = 124; \t\tpublic byte[] fcc2 = new byte[] { 's', 't', 'r', 'l' };  \t\tpublic AVIStreamList() {  \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(size))); \t\t\tbaos.write(fcc2); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIStreamHeader { \t\t\/\/ \t\t\/\/ FOURCC fcc; DWORD cb; FOURCC fccType; FOURCC fccHandler; DWORD dwFlags; WORD wPriority; WORD wLanguage; DWORD \t\t\/\/ dwInitialFrames; DWORD dwScale; DWORD dwRate; DWORD dwStart; DWORD dwLength; DWORD dwSuggestedBufferSize; \t\t\/\/ DWORD dwQuality; DWORD dwSampleSize; struct { short int left; short int top; short int right; short int \t\t\/\/ bottom; } rcFrame; \t\t\/\/  \t\tpublic byte[] fcc = new byte[] { 's', 't', 'r', 'h' }; \t\tpublic int cb = 64; \t\tpublic byte[] fccType = new byte[] { 'v', 'i', 'd', 's' }; \t\tpublic byte[] fccHandler = new byte[] { 'M', 'J', 'P', 'G' }; \t\tpublic int dwFlags = 0; \t\tpublic short wPriority = 0; \t\tpublic short wLanguage = 0; \t\tpublic int dwInitialFrames = 0; \t\tpublic int dwScale = 0; \/\/ microseconds \t\t\t\t\t\t\t\t\/\/ per \t\t\t\t\t\t\t\t\/\/ frame \t\tpublic int dwRate = 1000000; \/\/ dwRate \t\t\t\t\t\t\t\t\t\t\/\/ \/ \t\t\t\t\t\t\t\t\t\t\/\/ dwScale \t\t\t\t\t\t\t\t\t\t\/\/ = \t\t\t\t\t\t\t\t\t\t\/\/ frame \t\t\t\t\t\t\t\t\t\t\/\/ rate \t\tpublic int dwStart = 0; \t\tpublic int dwLength = 0; \/\/ num \t\t\t\t\t\t\t\t\t\/\/ frames \t\tpublic int dwSuggestedBufferSize = 0; \t\tpublic int dwQuality = -1; \t\tpublic int dwSampleSize = 0; \t\tpublic int left = 0; \t\tpublic int top = 0; \t\tpublic int right = 0; \t\tpublic int bottom = 0;  \t\tpublic AVIStreamHeader() { \t\t\tdwScale = (int) ((1.0 \/ framerate) * 1000000.0); \t\t\tdwLength = numFrames; \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(cb))); \t\t\tbaos.write(fccType); \t\t\tbaos.write(fccHandler); \t\t\tbaos.write(intBytes(swapInt(dwFlags))); \t\t\tbaos.write(shortBytes(swapShort(wPriority))); \t\t\tbaos.write(shortBytes(swapShort(wLanguage))); \t\t\tbaos.write(intBytes(swapInt(dwInitialFrames))); \t\t\tbaos.write(intBytes(swapInt(dwScale))); \t\t\tbaos.write(intBytes(swapInt(dwRate))); \t\t\tbaos.write(intBytes(swapInt(dwStart))); \t\t\tbaos.write(intBytes(swapInt(dwLength))); \t\t\tbaos.write(intBytes(swapInt(dwSuggestedBufferSize))); \t\t\tbaos.write(intBytes(swapInt(dwQuality))); \t\t\tbaos.write(intBytes(swapInt(dwSampleSize))); \t\t\tbaos.write(intBytes(swapInt(left))); \t\t\tbaos.write(intBytes(swapInt(top))); \t\t\tbaos.write(intBytes(swapInt(right))); \t\t\tbaos.write(intBytes(swapInt(bottom))); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIStreamFormat { \t\t\/\/ \t\t\/\/ FOURCC fcc; DWORD cb; DWORD biSize; LONG biWidth; LONG biHeight; WORD biPlanes; WORD biBitCount; DWORD \t\t\/\/ biCompression; DWORD biSizeImage; LONG biXPelsPerMeter; LONG biYPelsPerMeter; DWORD biClrUsed; DWORD \t\t\/\/ biClrImportant; \t\t\/\/  \t\tpublic byte[] fcc = new byte[] { 's', 't', 'r', 'f' }; \t\tpublic int cb = 40; \t\tpublic int biSize = 40; \/\/ same \t\t\t\t\t\t\t\t\/\/ as \t\t\t\t\t\t\t\t\/\/ cb \t\tpublic int biWidth = 0; \t\tpublic int biHeight = 0; \t\tpublic short biPlanes = 1; \t\tpublic short biBitCount = 24; \t\tpublic byte[] biCompression = new byte[] { 'M', 'J', 'P', 'G' }; \t\tpublic int biSizeImage = 0; \/\/ width \t\t\t\t\t\t\t\t\t\/\/ x \t\t\t\t\t\t\t\t\t\/\/ height \t\t\t\t\t\t\t\t\t\/\/ in \t\t\t\t\t\t\t\t\t\/\/ pixels \t\tpublic int biXPelsPerMeter = 0; \t\tpublic int biYPelsPerMeter = 0; \t\tpublic int biClrUsed = 0; \t\tpublic int biClrImportant = 0;  \t\tpublic AVIStreamFormat() { \t\t\tbiWidth = width; \t\t\tbiHeight = height; \t\t\tbiSizeImage = width * height; \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(cb))); \t\t\tbaos.write(intBytes(swapInt(biSize))); \t\t\tbaos.write(intBytes(swapInt(biWidth))); \t\t\tbaos.write(intBytes(swapInt(biHeight))); \t\t\tbaos.write(shortBytes(swapShort(biPlanes))); \t\t\tbaos.write(shortBytes(swapShort(biBitCount))); \t\t\tbaos.write(biCompression); \t\t\tbaos.write(intBytes(swapInt(biSizeImage))); \t\t\tbaos.write(intBytes(swapInt(biXPelsPerMeter))); \t\t\tbaos.write(intBytes(swapInt(biYPelsPerMeter))); \t\t\tbaos.write(intBytes(swapInt(biClrUsed))); \t\t\tbaos.write(intBytes(swapInt(biClrImportant))); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIMovieList { \t\tpublic byte[] fcc = new byte[] { 'L', 'I', 'S', 'T' }; \t\tpublic int listSize = 0; \t\tpublic byte[] fcc2 = new byte[] { 'm', 'o', 'v', 'i' };  \t\t\/\/ 00db size jpg image data ...  \t\tpublic AVIMovieList() {  \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(listSize))); \t\t\tbaos.write(fcc2); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIIndexList { \t\tpublic byte[] fcc = new byte[] { 'i', 'd', 'x', '1' }; \t\tpublic int cb = 0; \t\tpublic List ind = new ArrayList();  \t\tpublic AVIIndexList() {  \t\t}  \t\t@SuppressWarnings(&quot;unused&quot;) \t\tpublic void addAVIIndex(AVIIndex ai) { \t\t\tind.add(ai); \t\t}  \t\tpublic void addAVIIndex(int dwOffset, int dwSize) { \t\t\tind.add(new AVIIndex(dwOffset, dwSize)); \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tcb = 16 * ind.size();  \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(cb))); \t\t\tfor (int i = 0; i &lt; ind.size(); i++) { \t\t\t\tAVIIndex in = (AVIIndex) ind.get(i); \t\t\t\tbaos.write(in.toBytes()); \t\t\t}  \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIIndex { \t\tpublic byte[] fcc = new byte[] { '0', '0', 'd', 'b' }; \t\tpublic int dwFlags = 16; \t\tpublic int dwOffset = 0; \t\tpublic int dwSize = 0;  \t\tpublic AVIIndex(int dwOffset, int dwSize) { \t\t\tthis.dwOffset = dwOffset; \t\t\tthis.dwSize = dwSize; \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(dwFlags))); \t\t\tbaos.write(intBytes(swapInt(dwOffset))); \t\t\tbaos.write(intBytes(swapInt(dwSize))); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate class AVIJunk { \t\tpublic byte[] fcc = new byte[] { 'J', 'U', 'N', 'K' }; \t\tpublic int size = 1808; \t\tpublic byte[] data = new byte[size];  \t\tpublic AVIJunk() { \t\t\tArrays.fill(data, (byte) 0); \t\t}  \t\tpublic byte[] toBytes() throws Exception { \t\t\tByteArrayOutputStream baos = new ByteArrayOutputStream(); \t\t\tbaos.write(fcc); \t\t\tbaos.write(intBytes(swapInt(size))); \t\t\tbaos.write(data); \t\t\tbaos.close();  \t\t\treturn baos.toByteArray(); \t\t} \t}  \tprivate byte[] writeImageToBytes(Bitmap image) throws Exception { \t\tByteArrayOutputStream stream = new ByteArrayOutputStream(); \t\timage.compress(Bitmap.CompressFormat.JPEG, 100, stream); \t\tstream.close(); \t\treturn stream.toByteArray(); \t}  } <\/code><\/pre>\n<p>  <\/div>\n<\/div>\n<div class=\"spoiler\"><b class=\"spoiler_title\">activity_main.xml<\/b><\/p>\n<div class=\"spoiler_text\">\n<pre><code>&lt;RelativeLayout xmlns:android=&quot;http:\/\/schemas.android.com\/apk\/res\/android&quot;     xmlns:ads=&quot;http:\/\/schemas.android.com\/apk\/lib\/com.google.ads&quot;     xmlns:tools=&quot;http:\/\/schemas.android.com\/tools&quot;     android:layout_width=&quot;match_parent&quot;     android:layout_height=&quot;match_parent&quot;     android:background=&quot;@color\/appBackgroundColor&quot; &gt;      &lt;TextView         android:id=&quot;@+id\/centerEmptyText&quot;         android:layout_width=&quot;wrap_content&quot;         android:layout_height=&quot;wrap_content&quot;         android:layout_centerHorizontal=&quot;true&quot;         android:layout_centerVertical=&quot;true&quot; \/&gt;      &lt;SurfaceView         android:id=&quot;@+id\/mSurfaceView&quot;         android:layout_width=&quot;fill_parent&quot;         android:layout_height=&quot;fill_parent&quot;         android:layout_toRightOf=&quot;@+id\/centerEmptyText&quot; &gt;     &lt;\/SurfaceView&gt;      &lt;LinearLayout         xmlns:android=&quot;http:\/\/schemas.android.com\/apk\/res\/android&quot;         android:layout_width=&quot;fill_parent&quot;         android:layout_height=&quot;fill_parent&quot;         android:layout_marginRight=&quot;@dimen\/baseui_horizontal_margin&quot;         android:layout_toLeftOf=&quot;@+id\/centerEmptyText&quot;         android:orientation=&quot;vertical&quot; &gt;          &lt;TableLayout             xmlns:android=&quot;http:\/\/schemas.android.com\/apk\/res\/android&quot;             android:layout_width=&quot;wrap_content&quot;             android:layout_height=&quot;wrap_content&quot; &gt;              &lt;TableRow                 android:id=&quot;@+id\/periodRow&quot;                 android:layout_width=&quot;wrap_content&quot;                 android:layout_height=&quot;wrap_content&quot; &gt;                  &lt;TextView                     android:id=&quot;@+id\/periodText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:focusable=&quot;true&quot;                     android:focusableInTouchMode=&quot;true&quot;                     android:text=&quot;@string\/periodText&quot; &gt;                      &lt;requestFocus \/&gt;                 &lt;\/TextView&gt;                  &lt;EditText                     android:id=&quot;@+id\/periodEditText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:ems=&quot;2&quot;                     android:inputType=&quot;numberDecimal&quot;                     android:singleLine=&quot;true&quot; \/&gt;                  &lt;TextView                     android:id=&quot;@+id\/secondsText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:text=&quot;@string\/seconds&quot; \/&gt;             &lt;\/TableRow&gt;              &lt;TableRow                 android:id=&quot;@+id\/fpsRow&quot;                 android:layout_width=&quot;wrap_content&quot;                 android:layout_height=&quot;wrap_content&quot; &gt;                  &lt;TextView                     android:id=&quot;@+id\/framerateText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:focusable=&quot;true&quot;                     android:focusableInTouchMode=&quot;true&quot;                     android:text=&quot;@string\/framerateText&quot; \/&gt;                  &lt;EditText                     android:id=&quot;@+id\/fpsEditText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:ems=&quot;2&quot;                     android:inputType=&quot;numberDecimal&quot;                     android:singleLine=&quot;true&quot; \/&gt;                  &lt;TextView                     android:id=&quot;@+id\/fpsText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:text=&quot;@string\/fps&quot; \/&gt;             &lt;\/TableRow&gt;         &lt;\/TableLayout&gt;          &lt;TableLayout             xmlns:android=&quot;http:\/\/schemas.android.com\/apk\/res\/android&quot;             android:layout_width=&quot;wrap_content&quot;             android:layout_height=&quot;wrap_content&quot; &gt;              &lt;LinearLayout                 android:layout_width=&quot;fill_parent&quot;                 android:layout_height=&quot;wrap_content&quot;                 android:orientation=&quot;horizontal&quot; &gt;                  &lt;Button                     android:id=&quot;@+id\/startButton&quot;                     style=&quot;?android:attr\/buttonStyleSmall&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_gravity=&quot;center_vertical&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:layout_weight=&quot;1&quot;                     android:text=&quot;@string\/startButtonText&quot; \/&gt;                  &lt;Button                     android:id=&quot;@+id\/createButton&quot;                     style=&quot;?android:attr\/buttonStyleSmall&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_gravity=&quot;center_vertical&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:layout_weight=&quot;1&quot;                     android:text=&quot;@string\/createButtonText&quot; \/&gt;             &lt;\/LinearLayout&gt;              &lt;TableRow                 android:id=&quot;@+id\/totalsnapshotsRow&quot;                 android:layout_width=&quot;wrap_content&quot;                 android:layout_height=&quot;wrap_content&quot; &gt;                  &lt;TextView                     android:id=&quot;@+id\/totalsnapshotsText&quot;                     android:layout_width=&quot;wrap_content&quot;                     android:layout_height=&quot;wrap_content&quot;                     android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;                     android:text=&quot;@string\/totalsnapshotsText&quot; \/&gt;             &lt;\/TableRow&gt;         &lt;\/TableLayout&gt;          &lt;TextView             android:id=&quot;@+id\/modeText&quot;             android:layout_width=&quot;wrap_content&quot;             android:layout_height=&quot;wrap_content&quot;             android:layout_marginLeft=&quot;@dimen\/baseui_horizontal_margin&quot;             android:text=&quot;@string\/longestComment&quot; \/&gt;     &lt;\/LinearLayout&gt;  &lt;\/RelativeLayout&gt; <\/code><\/pre>\n<p>  <\/div>\n<\/div>\n<div class=\"spoiler\"><b class=\"spoiler_title\">AndroidManifest.xml<\/b><\/p>\n<div class=\"spoiler_text\">\n<pre><code>&lt;manifest xmlns:android=&quot;http:\/\/schemas.android.com\/apk\/res\/android&quot;     package=&quot;com.sample.timelapse&quot;     android:installLocation=&quot;preferExternal&quot;     android:versionCode=&quot;8&quot;     android:versionName=&quot;0.8&quot; &gt;      &lt;uses-sdk         android:minSdkVersion=&quot;8&quot;         android:targetSdkVersion=&quot;15&quot; \/&gt;      &lt;uses-permission android:name=&quot;android.permission.ACCESS_NETWORK_STATE&quot; \/&gt;     &lt;uses-permission android:name=&quot;android.permission.INTERNET&quot; \/&gt;     &lt;uses-permission android:name=&quot;android.permission.WRITE_EXTERNAL_STORAGE&quot; \/&gt;     &lt;uses-permission android:name=&quot;android.permission.VIBRATE&quot; \/&gt;     &lt;uses-permission android:name=&quot;android.permission.CAMERA&quot; \/&gt;     &lt;uses-permission android:name=&quot;android.permission.WAKE_LOCK&quot; \/&gt;      &lt;uses-feature android:name=&quot;android.hardware.camera&quot; \/&gt;     &lt;uses-feature         android:name=&quot;android.hardware.camera.autofocus&quot;         android:required=&quot;false&quot; \/&gt;     &lt;uses-feature         android:name=&quot;there.isnt.a.vibrate.feature&quot;         android:required=&quot;false&quot; \/&gt;      &lt;application         android:icon=&quot;@drawable\/ic_launcher&quot;         android:label=&quot;@string\/app_name&quot; &gt;         &lt;activity             android:name=&quot;.MainActivity&quot;             android:label=&quot;@string\/title_activity_main&quot;             android:screenOrientation=&quot;landscape&quot; &gt;             &lt;intent-filter&gt;                 &lt;action android:name=&quot;android.intent.action.MAIN&quot; \/&gt;                  &lt;category android:name=&quot;android.intent.category.LAUNCHER&quot; \/&gt;             &lt;\/intent-filter&gt;         &lt;\/activity&gt;     &lt;\/application&gt; &lt;\/manifest&gt; <\/code><\/pre>\n<p>  <\/div>\n<\/div>\n<div class=\"clear\"><\/div>\n<\/p><\/div>\n<p> \u0441\u0441\u044b\u043b\u043a\u0430 \u043d\u0430 \u043e\u0440\u0438\u0433\u0438\u043d\u0430\u043b \u0441\u0442\u0430\u0442\u044c\u0438 <a href=\"http:\/\/habrahabr.ru\/post\/172469\/\"> http:\/\/habrahabr.ru\/post\/172469\/<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<div class=\"content html_format\"> \t\t\t<img decoding=\"async\" src=\"http:\/\/img-fotki.yandex.ru\/get\/6426\/77014867.0\/0_a8a5a_3fa2f2e7_L.jpeg\" alt=\"image\" align=\"right\"\/>\u0414\u0430\u0432\u0430\u0439\u0442\u0435 \u043d\u0430\u043f\u0438\u0448\u0435\u043c \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0443 \u0434\u043b\u044f \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u0441\u0432\u043e\u0438\u0445 \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0445 \u0444\u0438\u043b\u044c\u043c\u043e\u0432 \u0432 \u0442\u0435\u0445\u043d\u0438\u043a\u0435 <a href=\"http:\/\/en.wikipedia.org\/wiki\/Time-lapse_photography\">Time Lapse<\/a>. \u0417\u0430\u0432\u043e\u0440\u0430\u0436\u0438\u0432\u0430\u044e\u0449\u0435\u0435 \u0432\u0438\u0434\u0435\u043e, \u0441\u043d\u044f\u0442\u043e\u0435 \u0432 \u044d\u0442\u043e\u0439 \u0442\u0435\u0445\u043d\u0438\u043a\u0435 \u0441 \u0431\u043e\u0440\u0442\u0430 \u041c\u041a\u0421, \u043c\u043e\u0436\u043d\u043e \u043f\u043e\u0441\u043c\u043e\u0442\u0440\u0435\u0442\u044c <a href=\"http:\/\/www.youtube.com\/watch?v=Ip2ZGND1I9Q\">\u0437\u0434\u0435\u0441\u044c<\/a>, \u0431\u043e\u043b\u0435\u0435 \u0434\u043e\u0441\u0442\u0443\u043f\u043d\u044b\u0439 \u0432\u0430\u0440\u0438\u0430\u043d\u0442, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u043e\u0436\u043d\u043e \u043f\u043e\u0432\u0442\u043e\u0440\u0438\u0442\u044c \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043e\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u043c\u043e\u0439 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u044b \u2014 <a href=\"http:\/\/www.youtube.com\/watch?v=Tt-juyvIWMQ\">\u0437\u0434\u0435\u0441\u044c<\/a>.<\/p>\n<p>  \u041f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u0438\u043c\u0435\u0435\u0442 \u043f\u0440\u043e\u0441\u0442\u043e\u0439 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0438 \u043d\u0435\u0441\u043b\u043e\u0436\u043d\u044b\u0439 \u043f\u0440\u0438\u043d\u0446\u0438\u043f \u0440\u0430\u0431\u043e\u0442\u044b:<br \/>  \u2022\u00a0\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c \u0437\u0430\u0434\u0430\u0435\u0442 \u043f\u0435\u0440\u0438\u043e\u0434\u0438\u0447\u043d\u043e\u0441\u0442\u044c \u0441\u043d\u0438\u043c\u043a\u043e\u0432 \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u043d\u043e\u0439 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 (\u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, 10 \u0441) \u0438 \u0436\u0435\u043b\u0430\u0435\u043c\u0443\u044e \u0447\u0430\u0441\u0442\u043e\u0442\u0443 \u043a\u0430\u0434\u0440\u043e\u0432 \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c\u043e\u0433\u043e \u0432\u0438\u0434\u0435\u043e (\u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, 25 \u043a\u0430\u0434\u0440\u043e\u0432 \u0432 \u0441\u0435\u043a\u0443\u043d\u0434\u0443);<br \/>  \u2022\u00a0\u043f\u043e\u0441\u043b\u0435 \u043d\u0430\u0436\u0430\u0442\u0438\u044f \u043a\u043d\u043e\u043f\u043a\u0438 \u00ab\u0421\u0442\u0430\u0440\u0442\u00bb\u00a0 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u043a\u0430\u0436\u0434\u044b\u0435 10 \u0441\u0435\u043a\u0443\u043d\u0434 \u0434\u0435\u043b\u0430\u0435\u0442 \u0444\u043e\u0442\u043e\u0433\u0440\u0430\u0444\u0438\u044e \u0438 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442 jpg-\u0444\u0430\u0439\u043b \u043d\u0430 SD-\u043a\u0430\u0440\u0442\u0443;<br \/>  \u2022\u00a0\u043f\u0440\u043e\u0446\u0435\u0434\u0443\u0440\u0430 \u043f\u043e\u0432\u0442\u043e\u0440\u044f\u0435\u0442\u0441\u044f \u0434\u043e \u043d\u0430\u0436\u0430\u0442\u0438\u044f \u043a\u043d\u043e\u043f\u043a\u0438\u00a0\u00ab\u0421\u0442\u043e\u043f\u00bb \u0438 \u00ab\u0421\u043e\u0437\u0434\u0430\u0442\u044c \u0432\u0438\u0434\u0435\u043e\u00bb, \u043f\u043e\u0441\u043b\u0435 \u0447\u0435\u0433\u043e \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u0444\u043e\u0442\u043e\u0433\u0440\u0430\u0444\u0438\u0439 \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0430\u0435\u0442\u0441\u044f \u0432 \u0432\u0438\u0434\u0435\u043e \u0444\u0430\u0439\u043b \u0444\u043e\u0440\u043c\u0430\u0442\u0430 <a href=\"http:\/\/ru.wikipedia.org\/wiki\/MJPEG#.D0.9F.D1.80.D0.B5.D0.B8.D0.BC.D1.83.D1.89.D0.B5.D1.81.D1.82.D0.B2.D0.B0_.D0.B8_.D0.BD.D0.B5.D0.B4.D0.BE.D1.81.D1.82.D0.B0.D1.82.D0.BA.D0.B8\">Motion JPEG<\/a>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u043e\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043e\u0442\u0441\u043d\u044f\u0442\u044b\u0439 \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b \u0432 250 \u0440\u0430\u0437 (25 * 10) \u0431\u044b\u0441\u0442\u0440\u0435\u0435 \u0440\u0435\u0430\u043b\u044c\u043d\u043e\u0439 \u0441\u043a\u043e\u0440\u043e\u0441\u0442\u0438 \u043f\u0440\u043e\u0438\u0441\u0445\u043e\u0434\u0438\u0432\u0448\u0438\u0445 \u0441\u043e\u0431\u044b\u0442\u0438\u0439.<\/p>\n<p>  \u0412 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0435 \u0434\u0432\u0430 \u043e\u0441\u043d\u043e\u0432\u043d\u044b\u0445 \u043a\u043b\u0430\u0441\u0441\u0430\u00a0\u2014\u00a0<em>MainActivity<\/em>, \u0437\u0430\u043d\u0438\u043c\u0430\u044e\u0449\u0438\u0439\u0441\u044f \u0432\u0437\u0430\u0438\u043c\u043e\u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0435\u043c \u0441 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0438 \u043d\u0430\u043a\u043e\u043f\u043b\u0435\u043d\u0438\u0435\u043c \u0441\u043d\u0438\u043c\u043a\u043e\u0432 \u0438\u00a0<em>MJPEGGenerator<\/em>, \u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0435\u043d\u043d\u044b\u0439 \u0437\u0430 \u043f\u0440\u0435\u0432\u0440\u0430\u0449\u0435\u043d\u0438\u0435 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0438\u0437\u043e\u0431\u0440\u0430\u0436\u0435\u043d\u0438\u0439 \u0432 \u0432\u0438\u0434\u0435\u043e \u0444\u0430\u0439\u043b.<\/p>\n<p>  \u041a\u043b\u0430\u0441\u0441 <em>MJPEGGenerator<\/em>, \u0432\u0437\u044f\u0442\u044b\u0439 \u0441 <a href=\"https:\/\/code.google.com\/p\/javadrone\/source\/browse\/src\/com\/codeminders\/ardrone\/util\/MJPEGGenerator.java?r=7503a6e1ba48b78dc1d79d741ef8c01b524dac91\">code.google.com<\/a>, \u0431\u044b\u043b \u0441\u043b\u0435\u0433\u043a\u0430 \u043f\u0435\u0440\u0435\u0434\u0435\u043b\u0430\u043d \u0432 \u0441\u0432\u044f\u0437\u0438 \u0441 \u0442\u0435\u043c, \u0447\u0442\u043e \u0432 Android Java \u043e\u0442\u0441\u0443\u0442\u0441\u0442\u0432\u0443\u0435\u0442 \u043f\u0430\u043a\u0435\u0442 java.awt.<\/p>\n<p>  \u041f\u0440\u043e\u0446\u0435\u0434\u0443\u0440\u044b \u0440\u0430\u0431\u043e\u0442\u044b \u0441 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 \u0431\u044b\u043b\u0438 \u043f\u0440\u0435\u0438\u043c\u0443\u0449\u0435\u0441\u0442\u0432\u0435\u043d\u043d\u043e \u0432\u0437\u044f\u0442\u044b \u0438\u0437 \u043c\u0430\u0442\u0435\u0440\u0438\u0430\u043b\u0430\u00a0<a href=\"http:\/\/habrahabr.ru\/post\/112272\/\">\u0420\u0430\u0431\u043e\u0442\u0430 \u0441 \u043a\u0430\u043c\u0435\u0440\u043e\u0439 \u0432 Android<\/a>, \u0433\u0434\u0435 \u0435\u0441\u0442\u044c \u0445\u043e\u0440\u043e\u0448\u0435\u0435 \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435 \u043f\u0440\u0438\u043c\u0435\u043d\u0435\u043d\u043d\u044b\u0445 \u0440\u0435\u0448\u0435\u043d\u0438\u0439, \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0430 \u00ab\u0437\u0430\u043b\u0438\u043f\u0430\u043d\u0438\u0439\u00bb \u043a\u0430\u043c\u0435\u0440\u044b \u043f\u043e\u0441\u043b\u0435 \u043b\u043e\u043a\u0430\/\u0430\u043d\u043b\u043e\u043a\u0430 Android-\u0443\u0441\u0442\u0440\u043e\u0439\u0441\u0442\u0432\u0430 \u0431\u044b\u043b\u0430 \u0443\u0441\u0442\u0440\u0430\u043d\u0435\u043d\u0430 \u0431\u043b\u0430\u0433\u043e\u0434\u0430\u0440\u044f\u00a0<a href=\"http:\/\/stackoverflow.com\/questions\/7186007\/camera-example-bug-when-locking-unlocking-device\">stackoverflow<\/a>.<\/p>\n<p>  \u041f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u0430 \u0431\u044b\u043b\u0430 \u043e\u0442\u043b\u0430\u0436\u0435\u043d\u0430 \u043d\u0430 \u043f\u043b\u0430\u043d\u0448\u0435\u0442\u0435 Prestigio MultiPad 7.0 Prime \u043f\u043e\u0434 Android 4.0.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[],"tags":[],"class_list":["post-172469","post","type-post","status-publish","format-standard","hentry"],"_links":{"self":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/172469","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=172469"}],"version-history":[{"count":0,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/172469\/revisions"}],"wp:attachment":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=172469"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=172469"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=172469"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}