Don't show supervised user as "already on this device" while they're being imported.
[chromium-blink-merge.git] / native_client_sdk / src / examples / demo / flock / flock.cc
blob9e1a639f8ed982d7ac20221162dd35a6516c5a12
1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include <stdio.h>
6 #include <stdlib.h>
7 #include <string.h>
8 #include <sys/mount.h>
10 #include <algorithm>
11 #include <sstream>
12 #include <string>
13 #include <vector>
15 #include "ppapi/c/pp_rect.h"
16 #include "ppapi/c/pp_size.h"
18 #include "ppapi_simple/ps_context_2d.h"
19 #include "ppapi_simple/ps_main.h"
21 #include "goose.h"
22 #include "sprite.h"
23 #include "vector2.h"
26 namespace {
27 // The goose sprites rotate in increments of 5 degrees.
28 const double kGooseHeadingIncrement = (5.0 * M_PI) / 180.0;
29 } // namespace
31 struct ImageFormat {
32 int width;
33 int height;
34 int channels;
37 Sprite* g_goose_sprite;
38 std::vector<Goose> g_geese;
39 std::vector<Vector2> g_attractors;
42 void ResetFlock(PSContext2D_t* ctx, size_t count) {
43 Vector2 center(0.5 * ctx->width, 0.5 * ctx->height);
45 g_geese.resize(count);
46 for (size_t i = 0; i < count; i++) {
47 double dx = (double) rand() / (double) RAND_MAX;
48 double dy = (double) rand() / (double) RAND_MAX;
49 g_geese[i] = Goose(center, Vector2(dx, dy));
53 void Render(PSContext2D_t* ctx) {
54 PSContext2DGetBuffer(ctx);
55 const size_t num_geese = g_geese.size();
57 if (NULL == g_goose_sprite) return;
58 if (NULL == ctx->data) return;
60 // Clear to WHITE
61 memset(ctx->data, 0xFF, ctx->stride * ctx->height);
63 int32_t sprite_side_length = g_goose_sprite->size().height();
64 pp::Rect sprite_src_rect(0, 0, sprite_side_length, sprite_side_length);
65 pp::Rect canvas_bounds(pp::Size(ctx->width, ctx->height));
68 // Run the simulation for each goose.
69 for (size_t i = 0; i < num_geese; i++) {
70 Goose& goose = g_geese[i];
72 // Update position and orientation
73 goose.SimulationTick(g_geese, g_attractors, canvas_bounds);
74 pp::Point dest_point(goose.location().x() - sprite_side_length / 2,
75 goose.location().y() - sprite_side_length / 2);
77 // Compute image to use
78 double heading = goose.velocity().Heading();
79 if (heading < 0.0)
80 heading = M_PI * 2.0 + heading;
82 int32_t sprite_index =
83 static_cast<int32_t>(heading / kGooseHeadingIncrement);
85 sprite_src_rect.set_x(sprite_index * sprite_side_length);
86 g_goose_sprite->CompositeFromRectToPoint(
87 sprite_src_rect,
88 ctx->data, canvas_bounds, 0,
89 dest_point);
92 PSContext2DSwapBuffer(ctx);
96 * Starting point for the module. We do not use main since it would
97 * collide with main in libppapi_cpp.
99 int example_main(int argc, char *argv[]) {
100 ImageFormat fmt;
101 uint32_t* buffer;
102 size_t len;
104 PSEventSetFilter(PSE_ALL);
106 // Mount the images directory as an HTTP resource.
107 mount("images", "/images", "httpfs", 0, "");
109 FILE* fp = fopen("/images/flock_green.raw", "rb");
110 fread(&fmt, sizeof(fmt), 1, fp);
112 len = fmt.width * fmt.height * fmt.channels;
113 buffer = new uint32_t[len];
114 fread(buffer, 1, len, fp);
115 fclose(fp);
117 g_goose_sprite = new Sprite(buffer, pp::Size(fmt.width, fmt.height), 0);
119 PSContext2D_t* ctx = PSContext2DAllocate(PP_IMAGEDATAFORMAT_BGRA_PREMUL);
120 ResetFlock(ctx, 50);
121 while (1) {
122 PSEvent* event;
124 // Consume all available events
125 while ((event = PSEventTryAcquire()) != NULL) {
126 PSContext2DHandleEvent(ctx, event);
127 PSEventRelease(event);
130 if (ctx->bound) {
131 Render(ctx);
132 } else {
133 // If not bound, wait for an event which may signal a context becoming
134 // available, instead of spinning.
135 event = PSEventWaitAcquire();
136 if (PSContext2DHandleEvent(ctx, event))
137 ResetFlock(ctx, 50);
138 PSEventRelease(event);
142 return 0;
146 * Register the function to call once the Instance Object is initialized.
147 * see: pappi_simple/ps_main.h
149 PPAPI_SIMPLE_REGISTER_MAIN(example_main);