(
Switch to Grids As Points
)
Horizontal extent:
Horizontal subset:
Lat/lon box
Proj X/Y box
Bounding box (in projection coords)
MaxY
MinX
MaxX
MinY
Horizontal stride:
Time subset:
Vertical subset:
Output format:
CF compliance:
Add 2D Lat/Lon to file


Galvanize
Delivers
Order Delivery
Menu
add
Royale with Cheese
$8.99
add
Ice Cream Biscuit
$7.99
add
Arugula Pie
$11.99
add
Smoked Swine
$14.99
Order
Item
Price
Subtotal:
Tax:
Total:
account_circle
Name
phone
Telephone
map
Address
Place Your Order
room_service


Random Questions
- Tell me one important component of web design
- What is typography matching
- What is usability
- What is consistency in web design?
Web Design Fundamentals
or the very basics of it
Precedence and placement
- What do you want users to do first?
- What are your goals/users?
Font Families
- Sans Serif
- Serif
- Cursive
- Monospace
- Others
Color Palettes
- Complementary colors
- Homogeneous colors
- Triads
- Analogous
- Monochromatic
- Adobe Color CC
Usability Testing
Usability Testing preparation
- Create a task list
- Get a consent form
- Plan the questions
- Run the test on yourself
- Open non-biased call for participants
Usability Testing steps
- Consent
- User is not being tested
- Try not to bias the user
- Ask user to think aloud
- Post-study survey
Likert Scale
What do you think?
- Strongly disagree
- disagree
- ok
- agree
- Strongly agree
More about likert scales
- Can be 3, 5, 7 or more responses
- Continuous or Discrete
- Middle response is the balance
Alternatives
- Mechanical Turk
- Behavior logs
- A/B Testing
- Controlled Experiments
- Expert reviews


I wanted to delete a folder with several files in it, on my computer. However, I was new to the computer's operating system and I wasn't confident about issuing the correct commands to my computer in order to delete the unwanted folder and the files sitting within it.
I used 3 problem sovling techniques to solve the problem:
I felt apprehensive at trying something new, but not fearful to the state where I froze. I always knew my problem had a straight-forward solution and that I merely required some re-assurance.
The coaches at EDA have seen the overwhelming majority of problems before, and can offer the guidance and advice for me to ultimately solve my own problems.
At one point in my career people wanted to engage my serivces as a damn good Data Analytics Specialist ... many moons ago.
I had too much work-on and it would have been impossible for me to deliver all the work that was being demanded of me without disappointing one or two clients.
Ask for help ...
I was concerned, losing work opportunities though losing potential clients was constantly on my mind as a self-employed person. But, I trusted in my fellows and friends around me, (and the clients for accepting a substitue for me).
That once again the greatest source of assistance is there in front of me: fellows and friends.
Pseudocode: I love this technique and it is often the first one I reach for when faced with a really challenging problem. It gives direction and clarity to problem solving. It provides a skeleton and placeholders to place the code.
Trying Something: I also love this technique. I've found that it is usually pretty inmprobable, especially as a beginner, to mess a task completely up. And that having a go, and trying somethings - different approaches - usually leads to furher learning opportunities and eventually deeper understanding of the task that was causing the problem.
Rubber Duck Method: Nope! This method to solving problem doesn't work that effectively for me, largely because there is no feedback-loop.
Reading Error Messages: The Error Messages often thrown-up by the computer can be somewhat cryptic, but they can often offer a good starting point for solving a problem.
Console Logging: I find this technique useful as it makes visible the invisible of what is going on behind the scenes. Again, they can offer a good starting point for solving a problem.
Googling: Undoubtedly a quick and powerful techinique, but I find it can offer only superficial offering to the learning process. I need to hear it from the human voice.
Asking Your Peers For Help: I'm never shy to ask for help. Questions aways offer the Questioner the best opportunity to learn. They can also help cement the knowledge of the Respondent. A kind of mutual benefit for both parties
Asking Coaches For Help: Ditto.
Improving Your Process With Reflection: I subscribe to Journaling which makes me reflect on my learning experiences. I have found reflection prepares me for future challenges.
The JavaScript Array object is a global object that is used in the construction of arrays; which are high-level, list-like objects...
like a container in which you might drop everyday objects of similar or differing kind.
.map() map() calls a provided callback function once for each element in an array, in order, and constructs a new array from the results ... it kinds of acts like a telephony service, picking out each of the everyday objects from the container one by one and placing them in turn into a new container.
.filter() filter() calls a provided callback function once for each element in an array, and constructs a new array of all the values for which callback returns a value that coerces to true ... it assists the map() function in its job of creating a new container through application of a rule-based filtering system: either accepting or rejecting the everyday objects to be placed in the new container,.
.reduce() reduce() method applies a function against an accumulator and each value of the array (from left-to-right) to reduce it to a single value ... if your everyday item is complex then the description of your everyday item will be reduce to a simple singular descriptive.


Lesson Plan Title: Password Strength
Concept / Topic To Teach:
Accounts are only as secure as their passwords. Most users have the same weak password everywhere. If you want to protect them against brute-force-attacks your application should have good requirements for passwords. The password should contain lower case letters, capitals, numbers and special characters. The longer the password, the better, consider using a passphrase instead. For more information see: OWASP proper password strength.General Goal(s):
For this exercise, your job is to test several passwords on https://howsecureismypassword.net/


{{< layout}} {{$propositionHeader}}{{/propositionHeader}} {{$pageTitle}}Apply for, renew or replace a UK passport{{/pageTitle}} {{$header}}
When you apply for a UK passport online, we can access your digital photo automatically.
This is only possible for some applications. Before you access your photo, we'll check which type of application you're making.
Continue


Configure the card deck which is used for this module. You can filter the cards by which are owned by players and change ownership of cards too.


{% extends "layout.html" %} {% block article_body %} {% markdown %} [Ipsos MORI](https://www.ft.com/topics/organisations/Ipsos_MORI) has published the results of its annual [Perils of Perception poll](http://perils.ipsos.com/) of 40 countries, revealing [some startling disparities](https://www.ft.com/content/bed2e788-c154-11e6-9bca-2b93a6856354?bhgh) between people's preconceptions about their country and the realities. Take our quiz to see how your perceptions compare to those of the country overall, as well as to other quiz-takers.
Loading quiz…


[gecode-users] Reporting memory usage
Filip Konvička
filip.konvicka at logis.cz
Thu Oct 30 16:41:31 CET 2008
> Regions work as follows: if one has a space one can get a region for
> that space. One can allocate memory (very very efficiently) from a
> region. However, the memory will only be freed when the region is
> destructed. (Actually, what happens there is that all spaces for one
> thread share a small memory area and that a Region provides access to
> this shared memory area. If a request cannot be fulfilled from this
> area, memory will be allocated transparently from the heap). Very simple
> as you don't have to deallocate to a region, very efficient, and much
> cleaner than alloca.
Great. So I reckon you can explicitly destroy the region as soon as
you've finished using it. It'll be great fun using fast_pool_allocator
on top of Gecode regions :-)
> So, what I would like to ask you guys: would you be willing to
>
> - Write stl allocators for both regions and spaces.
>
> - Test with your own programs that these allocators work.
>
> - Send me a patch for Gecode 3.0.0 so that I can integrate your stuff
> into the trunk into gecode/support (as a separate file).
>
> - Test the stuff again after I integrated.
>
> - Negotiate among you who does what.
I'll try to port the code to support Gecode 3.0.0 memory API. It is
little code so I think it should be fairly easy.
So Gustavo, I propose that you wait for me to do the initial work and
once I post the new version here you can try it out.
As for testing...hm...I've not upgraded to 3.0 yet, so I don't have much
to test with ATM. Much of what we have is somehow related to FloatVars,
which probably don't work with 3.0 yet. The rest is some scheduling
stuff, so I guess I could run these as we're using some custom data
structures there (mostly vectors, but maybe also some hashmaps, will
have to check).
BTW, I have a few more fixes for floatvars regarding memory management,
as dispose() was not properly called for some branchings etc., so I
guess I should post (yet) another update.
Cheers,
Filip
More information about the gecode-users
mailing list


This page describes cameras and their use in Project: 3D
Craft. This section is broken into three parts, a discussion of
cameras, a discussion of the p3dc_CMRA
type, and then the APIs that take cameras as their first
parameter (the Camera API).
The p3dc_CMRA type is used to define all of the properties of a virtual camera.
| Member | Type | Description |
|---|---|---|
| origin | p3dc_PNT3 | This is the location of the camera in the world. The vector from it to the look-at point defined below is the view's Z axis. |
| look | p3dc_PNT3 | This is the point in the world where the camera is supposed to point. By default it is 0,0,0 |
| up | p3dc_PNT3 | This is a unit vector that defines "up" for the camera. It is an error to have the look-at vector and the up vector match. |
| twist | p3dc_FLOAT | This is defined is a rotation about the camera's Z axis. It is currently defined as being defined to occur before camera re-location. |
| far_p | p3dc_FLOAT | This value defines the "back" of the viewing frustum. Anything beyond this point is clipped out of existence. |
| near_p | p3dc_FLOAT | This is the distance from the camera origin to the 'near' plane. If the near plane is the screen this would be 0. |
| fov | p3dc_FLOAT | This is the field of view for the camera. It must be greater than 0 and less than 180 degrees. Attempting to set it to values outside this range is undefined. |
| W2V | p3dc_XFRM | This transform will transform a point from world co-ordinates into this camera's viewing co-ordinates. It is affine and does no perspective projection. I use it for models that are moving about in the world. |
| V2S | p3dc_XFRM | This is the "view-to-screen" transform and contains the perspective projection of the transformed world view on to the 2D screen view. |
| view_xfrm | p3dc_XFRM | This transform is the product of W2V*V2S and will transform a point from the world, into the view space of the camera, apply a perspective projection and make the point ready for clipping. It is used extensively when drawing the scene on the screen. |
| vp | p3dc_VIEW | This field is a view port that is used by the GAL layer to convert from camera co-ordinates into screen co-ordinates. (see below) |
The p3dc_VIEW type is used to define the mapping between a camera and the screen. The camera realizes the scene in ideal (i.e. -1.0, 1.0) co-ordinates and the view is used to map those into screen co-ordinates.
| Member | Type | Description |
|---|---|---|
| scale_x | p3dc_FLOAT | Scaling factor to convert from -1.0 to 1.0 into screen co-ordinates. |
| scale_y | p3dc_FLOAT | Scaling factor for the vertical screen access to convert from -1.0 to 1.0 in Y space. |
| center_x | p3dc_FLOAT | This represents the screen X co-ordinate of point "0,0". |
| center_y | p3dc_FLOAT | This represents the screen Y co-ordinate for point "0,0". |
In the "real" world, cameras focus light through lenses on to either a piece of film or a light sensitive detector of some kind (say a CCD). The result is that a 3-dimensional scene is rendered on to the plane of the detector/film/whatever. What certainly wasn't so clear to me was how to simulate that in a computer program.
The p3dc_CMRA
data structure is one of the more important ones in the library.
This structure defines a "view" into the 3-D world that
projects on to a rectangular 2-D plane (the screen). The camera
structure has three main parts:
These components form the basis of a simple viewing system and the camera API is all about manipulating these transforms to simulate putting the camera at a particular point in space and pointing it at something.
This viewing system is incomplete in that it is not as general as the PHIGS system or others where the perspective reference point (PRP) can be specified, instead, the PRP is always centered in the view.
The camera system does however let you set a variety of parameters to suit your needs. In particular it allows you to set the "near" and "far" clipping planes, the "twist" of the camera, its "up" vector, where it is "looking", and its is "location." Each of these parameters are represented in the structure by the fields, near_p, far_p, twist, up, look, and origin. The parameters are combined to create the transforms necessary to render a particular view. The result of all the camera calculations is a matrix, view_xfrm, that is used to render the scene.
Once the camera is set up, you call the rendering API to draw the scene with that camera's transforms and then display the resulting frame.
Step one in initializing a camera is figuring out how to transform world co-ordinates such that the camera's origin is at 0,0,0 and the Z axis points straight away from the camera (into the screen). This computation is done using the function p3dc_camera_xfrm. This function does its work by working backward from what you want, let me explain.
The p3dc_CMRA
structure contains the origin of the camera O
(I'm using upper case letters to indicate vectors. Vectors have
three scalar components x, y, z) and the point in space where the
camera is looking L.
Using these to co-ordinates in world space we can
compute the unit vector that points from O
to L by performing
the vector subtraction of L
and O and
normalizing the result like so:
F = | L - O |
The result, F,
is the z axis of the new view. (This vector is called F to distinguish it from
the world's z axis, the view's three basis vectors are Right, Up, and Forward which related to x,
y, and z in a standard
Cartesian system.) To compute R,
the view's x axis, we compute the cross product of the up
vector stored in the p3dc_CMRA
and the just computed F
vector and normalize it to be a unit vector. This can be written
as:
R = | up x F |
At this point we have two of the final basis vectors (F and R). With these two vectors we can compute the up vector, U, by computing the cross product of F and R and normalizing the result like so:
U = | R x F |
After figuring out the desired U vector we have the basis vectors for the view transform. (R, U, and F.)
Now the twist of the camera has to be factored into the matrix. The twist of the camera is the rotation of the camera about its own Z axis. This computation is done by multiplying this view transform with another transform that rotates about the F axis. This results in a new set of basis vectors for the view which I call R', U' and F'. Note that there is one bit of cleverness going on here that isn't immediately obvious. The camera transform is an inverse transform which means it spins the world about as opposed to camera spinning about. Since the matrix that is computed is both affine and orthonormal the inverse of the matrix can be computed by swapping the rows and columns. Thus where I would put each vector into a column in a 'regular' matrix I put the camera's view vectors into the resulting matrix in rows.
The final step is to place the camera origin in this new space. That could be represented as:
| R'x R'y R'z | P = | U'x U'y U'z | | Ox Oy Oz | | F'x F'y F'z |
The transformed origin, referred to above as P, is placed with the view basis vectors into the 4 x 4 transformation matrix to complete the world to view transformation as follows:
| R'x R'y R'z Px | | U'x U'y U'z Py | | F'x F'y F'z Pz | | 0 0 0 1 |
The result of these computations is stored in the camera's W2V transform. The W2V transformed is used by the model code as well as part of the computation of the models eventual model space to screen space transformation.
Now for something a bit different. Going from the view on to the screen.
Going from view to screen is easy when you understand it, and impossibly opaque when you don't. This is where you need to know a bit about matrix math to understand exactly how the Perspective Transformation actually works.
To start, lets explain how perspective works.  This can be modeled as a "pin hole" camera. (Using a pin-hole camera is preferable since there are no focal length and focal depth issues associated with them). Things that are closer obscure more of your vision than things that are farther away. Thus the things farther away look smaller although your brain auto-compensates and tells you they aren't really small at all.
The typical "newbie" way of achieving a perspective view then is to divide the X and Y view co-ordinates by Z before drawing them on the screen. The newbie technique works well and is satisfactory for many game situations or times when control of the view isn't critical.
I of course wanted to know exactly what it meant to divide by Z and that lead me to reading several discussions on the perspective transformation.
The bottom line is that you can think of a pin hole camera as defining two right triangles, as shown in the image to the right (click on it for a larger view). The value H is reflected through the pin-hole to the value h behind it. Scaling of H to h is defined by the ratio of H to D which, from basic geometry of similar triangles, is identical to the ratio of h to d. Further, the ratio is related to the angle a which is called the "field of view."
So if you fix the field of view to be 90º then the angle in the right triangle becomes 45º and the ratio between D and H is 1.0. Thus simply dividing your X and Y coordinate by Z is a simple way of implementing a perspective transformation with a fixed field of view of 90º.
But what about other fields of view and why are they important? Looking at the figure above you can probably see that if the field of view is narrower then the distance at H will be shorter. However, the screen remains the same size, so displaying less of the view on the same size screen causes the perception that the view is enlarged or zoomed.
Looking at documentation on 35MM camera lenses it became clear that what defined a "tele-photo" lens is the distance of its focal length. The focal length of the lens is just d in the figure, and since h is fixed, changing the focal length changes the field of view. Longer focal length, smaller field of view, and larger zoom factor.
So to manage zooming in our simulated camera we need to do something to the X and Y co-ordinates and that something is we need to scale them. How much? By the same ratio d/h that we used when figuring out the relationship of H to h. To do this with a matrix is easy, we put the value d/h into the [0,0] and [1,1] locations and that does the scaling for us. But we aren't quite done. We are transforming from the view to the screen and it will be rare that everything in the screen will fit, so we will have to clip the scene to the screen boundaries.
A lot of people get confused by clipping. I know I did, and still do now and then, but I think I've got it nailed now. I implement clipping using the Sutherland-Hodgman clipping algorithm. Which is a very simple algorithm for walking the vertices of a polygon, and inserting new vertices whenever the current vertex and the next vertex are on different sides of the clipping view. But what is the clipping view?
Imagine for a moment that you want to clip in 3-D and to simplify things you make some assumptions which are:
This is a pretty easy space to clip to right? Just check to see if -1.0 < x < 1.0, and -1.0 < y < 1.0, and finally 0.0 < z < 1.0. If a vertex is beyond one of those boundaries then you need to clip it because the "view" is only what is inside the box.
As it turns out this is exactly what Sutherland-Hodgman does and it does it by considering each polygon in the scene. The algorithm starts with the second vertex (remember the minimum polygon is a triangle which has three vertices!) and compares it with the previous vertex. If both are outside the box, nothing happens, if one is inside and one is outside the box then a new vertex is created and "output" where the line segment transitions to being "inside" the box, and if both are inside then the current vertex is output and the next step is done. When the last vertex is reached the algorithm "rolls over" to the first vertex (remember it skipped it at the start) and compares the first vertex to the last vertex outputting it as appropriate. If the list of "outputted" vertices is zero then the polygon is outside the box completely, otherwise the new list is the clipped version of the polygon.
Note that the algorithm operates on each plane intersection test (x < -1.0 for example) iteratively. The result of running this algorithm for all of the plane intersection tests (x > -1.0, x < 1.0, y > -1.0, ... ) is a polygon that is completely inside the box.
Yes, this takes up some computer time to do, however most polygons do not need to be clipped and this step can be skipped on those polygons that are completely visible. A very fast visibility test is done with outcodes and is described in the source.
"But how do we get to this 'ideal' world?" With a transformation of course! Remember that that by scaling the x and y values by the ratio of the field of view triangle we converted from an arbitrary field of view to a 90 field of view? Well in that view we can make a box by dividing x and y by z! So now Xs = x / z and when z = x, Xs will be 1.0 ! But that is a lot of divisions that we would just as soon avoid so instead of comparing x to 1.0 we can simply compare x to z!
So I make two changes to the V2S matrix, in addition to the x and y scaling I add to [3,2] the value 1.0, to [3,3] the value 0.0, and to [2,2] and [2,3] the values 1 / (far_p - near_p) and -near_p / (far_p - near_p) respectively. This makes the matrix look like this:
| d/h 0.0 0.0 0.0 | | 0.0 d/h 0.0 0.0 | | 1.0 - near_p | | 0.0 0.0 ---------------- ----------------- | | (far_p - near_p) (far_p - near_p) | | 0.0 0.0 1.0 0.0 |
And when I multiply by this matrix there are a couple of interesting effects. The fourth element 'w' in the resulting vector R becomes Rw = Vx * 0.0 + Vy * 0.0 + Vz * 1.0 + Vw * 0.0, or more simply the value of Vz gets copied into Rw. And the value in Rz gets computed as Rz = Vx * 0.0 + Vy * 0.0 + Vz /(far_p-near_p) + (Vw * near_p) / (far_p - near_p) and since Vw is always 1.0 that reduces (with a bit of algebra) to Rz = (Vz - near_p)/(far_p - near_p). Which, if you were to map it out, re-maps Rz to be a number that moves linearly between 0 when Vz = near_p and 1.0 when Vz = far_p. This linearity is used to our advantage to get the maximum resolution out of the 16 bit w-buffer available on the Voodoo style hardware accelerator.
Finally, the view port may not be square, and as such the ratio of the width to the height is not 1.0. To correct for a non-square view port, the term in location [0,0] is multiplied by the ratio of the width to the height to "squeeze" the box along its width when doing clipping calculations.
After computing the world to view, and view to screen
transformations, the results are multiplied to create the final
composite transformation and stored in the structure member view_xfrm.
Additionally the structure VP which is of type p3dc_VIEW
contains the scaling factor for the screen x and screen y
co-ordinates. The rendering pipeline then works as follows:
1. Note that the depth computation is pretty specific to the 3Dfx hardware. The "one over w" or oow value ranges from 1/1.0 to 1/65536 using this technique.
Once the hardware layer has the screen co-ordinates and the depth it has all the information necessary to render the primitive into the frame buffer. When the frame buffer is made visible to the user, the user sees the 3-D world rendered from the viewpoint of the "camera" in world space. Voila' we're done!
These are the interfaces that are used to allocate, free, and manipulate cameras.
p3dc_CMRA *p3dc_new_camera( p3dc_FLOAT fov, p3dc_FLOAT x, y, z )
This function allocates a new camera from the heap and initializes the camera's transforms based on the field of view passed in as fov and the position in x, y, and z. The look-at point is assumed to be (0, 0, 0) and the up direction of the camera is assumed to be the same as the world's Y axis.
void p3dc_init_camera(p3dc_CMRA *cam, p3dc_FLOAT fov, p3dc_FLOAT x, y, z )
This interface initializes (or re-initializes) a p3dc_CMRA structure. The camera's look-at point is presumed to be (0, 0, 0) and the up vector is presumed to be the world's positive Y axis.
The parameters that control the field of view, clipping boundaries, etc, can be set individually or by using the very flexible p3dc_set_camera interface. Each of these interfaces is defined as p3dc_set_camera_XXX where XXX is the parameter of interest.
A couple of notes you should be aware of:
int p3dc_set_camera( p3dc_CMRA *camera, int parameter, ... , 0 )
This is the generic version of the camera parameter setting code. There are several parameters that can be set, they are identified by a constant and take at least one parameter. Parameters are passed to the function call as parameter/argument tuples. In all cases the argument is currently a pointer but this may change with future parameters. The constants and their parameters are:
Parameter Argument Description P3DC_CAMERA_ORIGIN p3dc_PNT3 *origin The x, y, and z components of origin are used to define the new location of the camera in world space. P3DC_CAMERA_VIEW p3dc_XFRM *transform The contents of transform are copied into the camera's W2V transform and the view transform is recomputed. P3DC_CAMERA_SCREEN p3dc_XFRM *transform The contents transform are copied into the camera's V2S transform and the view transform is recomputed. P3DC_CAMERA_ROLL p3dc_FLOAT *angle A rotation of angle degrees is applied to the camera's world to view transform about the local Z axis. Note: roll is relative to the current position, not the "up" vector. P3DC_CAMERA_YAW p3dc_FLOAT *angle A rotation of angle degrees is applied to the camera's world to view transform about the local Y axis. Note: yaw angle is relative to the current position. P3DC_CAMERA_PITCH p3dc_FLOAT *angle A rotation of angle degrees is applied to the camera's world to view transform about the local X axis. Note: pitch angle is relative to the current position. P3DC_CAMERA_FOV p3dc_FLOAT *angle The camera's field of view is set to angle degrees. This will force the V2S transform to be recomputed from the camera's parameters. P3DC_CAMERA_UP p3dc_PNT3 *up The camera's notion of "up" is set to be equal to the up parameter. Cameras are initialized with an up parameter of (0, 1, 0) (the world Y axis). P3DC_CAMERA_FAR p3dc_FLOAT *dist The camera's far clipping plane is set to dist. Objects that are farther away than this distance will not be rendered on the screen. Camera's initially have a far clipping plane set to 2048.0 P3DC_CAMERA_NEAR p3dc_FLOAT *dist The camera's near clipping plane is set to dist. Objects that are closer than this are clipped. This value must be greater than or equal to 1.0. P3DC_CAMERA_TWIST p3dc_FLOAT *angle The cameras twist is set to angle. Unlike roll above this is specified in degrees from the camera's local Up vector. P3DC_CAMERA_LOOK p3dc_PNT3 *target The camera is oriented to look at target in world co-ordinates. P3DC_CAMERA_DIR p3dc_PNT3 *normal The cameral is aligned the normal vector normal in world space. Once all parameters and their arguments are included, you must include a 0 to indicate the end of the list. This is a source of bugs, sorry about that. As a usage example, consider locating a camera at 10, 5, -5 and pointing it at the point 5, 5, 5:
p3dc_CMRA *cam = p3dc_new_camera(...); p3dc_PNT3 location, interest; location.x = 10; location.y = 5; location.z = -5; interest.x = 5; interest.y = 5; interest.z = 5; p3dc_set_camera(cam, P3DC_CAMERA_ORIGIN, &location, P3DC_CAMERA_LOOK, &interest, 0); ...In the above example the camera is located and pointed in the same call to p3dc_set_camera.
While the above routine is technically all you need, sometimes it is convenient to set the camera's parameters individually, this also allows for some nicer syntax. These routines should all call p3dc_set_camera or just be #defines to calls to p3dc_set_camera however given the evolutionary nature of the code not all of them are yet.
void p3dc_set_camera_fov( p3dc_CMRA *cam, p3dc_FLOAT fov )
This function sets the field of view of the camera to be fov. This has the same effect as a "zoom" lens in that the narrower the field of view, the more magnified the view appears. Note that this changes affects the V2S transform but not the W2V transform in the camera structure.
void p3dc_set_camera_target( p3dc_CMRA *cam, p3dc_FLOAT x, y, z, p3dc_PNT3 *up, p3dc_FLOAT twist)
This function is one of two orientation functions for cameras. This one "targets" the camera at a point in world space and sets its "up" orientation. To point the camera at a model (for following it for example) you might use
p3dc_target_camera(mycamera, x, y, z, &up_vector, 0);Which would have the effect of targeting the camera at a point (x, y, z) in world space, using up_vector as its notion of up, and not twisted about the camera's view vector at all. If the up parameter is NULL then the world Y axis is presumed to represent the up direction.
void p3dc_set_camera_origin( p3dc_CMRA *cam, p3dc_FLOAT x, y, z)
This function positions the camera at the point (x, y, z) in the world. Note that the camera will re-orient itself to continue looking at its "look" point.
void p3dc_set_camera_dir( p3dc_CMRA *cam, p3dc_PNT3 *dir, *up, p3dc_FLOAT twist )
This function is a general purpose camera orientation routine. It takes a unit vector pointing in the same direction that you want the camera to point, a unit vector pointing in the direction of "up" (if this is NULL then the Y axis is assumed to be pointing up) and a "twist" value which defines how the camera is rotated about its view axis. Note that twist and up are related in that the camera is presumed to be at zero twist when the camera's "up" vector is, as closely as possible, aligned with the up vector. So an up vector of (0, -1, 0) with a twist of 0 degrees, is equivalent to an up vector of (0,1,0) with a twist of 180 degrees.
void p3dc_set_camera_roll( p3dc_CMRA *cam, p3dc_FLOAT angle )
This function changes the camera's orientation along its "look" vector (nominally the Z vector). Positive angles roll the camera clockwise, and negative angles roll the camera counter-clockwise. The roll angle is relative to the current position and orientation of the camera. You can re-zero the camera to zero roll by resetting its "up" vector with p3dc_set_camera.
void p3dc_set_camera_pitch( p3dc_CMRA *cam, p3dc_FLOAT angle )
This function changes the "pitch" of the camera. Intuitively this causes the camera to "look up" when the angle is positive, and to "look down" when the angles is negative. The change is relative to the current camera position so calling this function twice with an angle of 5 degrees will cause the camera to end up looking up by 10 degrees (twice 5 is 10, get it?)
void p3dc_set_camera_yaw( p3dc_CMRA *cam, p3dc_FLOAT angle )
Can you guess what this one does? Ok this function turns the camera "right" when the angle is positive and "left" when the angle is negative. Again the change is relative to the current camera position so if you started out looking straight ahead and called this once with the value of 10 and once with the value of -15 for angle then the camera would end up oriented such that it was pointed 5 degrees left of where it started out.
void p3dc_set_camera_window( p3dc_CMRA *cam, int width, int height )
This function sets the scaling of X and Y in the view structure such that the resulting view rendered by the camera will be width pixels wide by height pixels high. Centered of course where the camera was centered on the screen before.
void p3dc_set_camera_frame( p3dc_CMRA *cam, int x, int y, int width, int height )
This function configures the camera's view so that the lower left corner of the view is at [x, y] and the camera view is width pixels wide by height pixels tall. What is unclear to me is what exactly this means. One of the areas I'm trying to figure out is the relationship between camera parameters and perceived size. How do I create an Ant's view of the world? A dog's? A person's ? Certainly dog's eyes and people eyes are about the same size but not an Ant's. And of course every thing is "bigger" but does an ant sitting on my shoulder see the world as I do? I don't think so. Lots to learn in this area.
void p3dc_set_camera_view( p3dc_CMRA *cam, p3dc_XFRM *new_W2V )
I wrote this function originally to allow me to play around with different ways of calculating the world to view transformation. See the file
cameratest.c
for usage. It simply copies the transform into the camera and recalculates the view transform based on the camera's existing view to screen transform.
void p3dc_set_camera_screen( p3dc_CMRA *cam, p3dc_XFRM *new_V2S )
I wrote this function originally to allow me to play around with different ways of calculating the view to screen transformation. See the file
perspective.c
for usage. It simply copies the transform into the camera and recalculates the view transform based on the camera's existing world to view transform.
void p3dc_set_camera_near( p3dc_CMRA *cam, p3dc_FLOAT d )
This function sets the point where objects close to the camera get clipped. Since our camera is a pin-hole camera there is a singularity at 0 but it turns out that in reality the number is nearly always 1.0 This is because it is easier to think in whole numbers, however you can set this to be smaller if you need to..
void p3dc_set_camera_far( p3dc_CMRA *cam, p3dc_FLOAT MaxZ )
This function sets the farthest Z point I care about. More importantly when I am rendering to the w buffer, values in Z are scaled to go between 0 and this value. That helps prevent clipping artifacts, and most of the time things farther away than this aren't visible anyway so why bother drawing them.


SUBSTRING()
SUBSTRING(value, offset, length) → substring
Return a substring of value.
- value (string): a string
- offset (number): start at offset, offsets start at position 0
- length (number, optional): at most length characters, omit to get the
substring from offset to the end of the string
- returns substring (string): a substring of value


Say Hello
Not casting the HTMLElement works but warns about type violation
Using a String array works but warns type violation
Generate Student


Class: Aws::GameLift::Types::GameServer
| Relationships & Source Files | |
| Super Chains via Extension / Inclusion / Inheritance | |
|
Class Chain:
self,
Struct
|
|
|
Instance Chain:
self,
::Aws::Structure ,
Struct
|
|
| Inherits: |
Struct
|
| Defined in: | gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb |
Overview
This data type is used with the Amazon GameLift FleetIQ and game server groups.
Properties describing a game server that is running on an instance in a game server group.
A game server is created by a successful call to RegisterGameServer
and deleted by calling DeregisterGameServer
. A game server is
claimed to host a game session by calling ClaimGameServer
.
Constant Summary
Instance Attribute Summary
-
#claim_status ⇒ String
rw
Indicates when an available game server has been reserved for gameplay but has not yet started hosting a game.
-
#connection_info ⇒ String
rw
The port and IP address that must be used to establish a client connection to the game server.
-
#game_server_data ⇒ String
rw
A set of custom game server properties, formatted as a single string value.
-
#game_server_group_arn ⇒ String
rw
The ARN identifier for the game server group where the game server is located.
-
#game_server_group_name ⇒ String
rw
A unique identifier for the game server group where the game server is running.
-
#game_server_id ⇒ String
rw
A custom string that uniquely identifies the game server.
-
#instance_id ⇒ String
rw
The unique identifier for the instance where the game server is running.
-
#last_claim_time ⇒ Time
rw
Timestamp that indicates the last time the game server was claimed.
-
#last_health_check_time ⇒ Time
rw
Timestamp that indicates the last time the game server was updated with health status.
-
#registration_time ⇒ Time
rw
Timestamp that indicates when the game server registered.
-
#utilization_status ⇒ String
rw
Indicates whether the game server is currently available for new games or is busy.
Instance Method Summary
Instance Attribute Details
#claim_status ⇒ String
(rw)
Indicates when an available game server has been reserved for
gameplay but has not yet started hosting a game. Once it is claimed,
the game server remains in CLAIMED
status for a maximum of one
minute. During this time, game clients connect to the game server to
start the game and trigger the game server to update its utilization
status. After one minute, the game server claim status reverts to
null.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#connection_info ⇒ String
(rw)
The port and IP address that must be used to establish a client connection to the game server.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#game_server_data ⇒ String
(rw)
A set of custom game server properties, formatted as a single string value. This data is passed to a game client or service when it requests information on game servers.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#game_server_group_arn ⇒ String
(rw)
The ARN identifier for the game server group where the game server is located.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#game_server_group_name ⇒ String
(rw)
A unique identifier for the game server group where the game server is running.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#game_server_id ⇒ String
(rw)
A custom string that uniquely identifies the game server. Game server IDs are developer-defined and are unique across all game server groups in an Amazon Web Services account.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#instance_id ⇒ String
(rw)
The unique identifier for the instance where the game server is
running. This ID is available in the instance metadata. ::Aws::EC2
instance
IDs use a 17-character format, for example: i-1234567890abcdef0
.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#last_claim_time ⇒ Time
(rw)
Timestamp that indicates the last time the game server was claimed.
The format is a number expressed in Unix time as milliseconds (for
example "1469498468.057"
). This value is used to calculate when a
claimed game server's status should revert to null.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#last_health_check_time ⇒ Time
(rw)
Timestamp that indicates the last time the game server was updated
with health status. The format is a number expressed in Unix time as
milliseconds (for example "1469498468.057"
). After game server
registration, this property is only changed when a game server
update specifies a health check value.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#registration_time ⇒ Time
(rw)
Timestamp that indicates when the game server registered. The format
is a number expressed in Unix time as milliseconds (for example
"1469498468.057"
).
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end
#utilization_status ⇒ String
(rw)
Indicates whether the game server is currently available for new games or is busy. Possible statuses include:
AVAILABLE
- The game server is available to be claimed. A game server that has been claimed remains in this status until it reports game hosting activity.UTILIZED
- The game server is currently hosting a game session with players.
# File 'gems/aws-sdk-gamelift/lib/aws-sdk-gamelift/types.rb', line 4433
class GameServer < Struct.new( :game_server_group_name, :game_server_group_arn, :game_server_id, :instance_id, :connection_info, :game_server_data, :claim_status, :utilization_status, :registration_time, :last_claim_time, :last_health_check_time) SENSITIVE = [] include Aws::Structure end


Akufo-Addo appointees are very stingy – NPP grassroot campaigners
The National Chairman of a Pro-NPP group, NPP Grassroot Campaigners, Mr. Emmanuel Nana Apor has lambasted appointees of President Akufo-Addo describing them as stingy.
According to him, most of the MMDCEs, Ministers and CEO’s of public institutions are so ungenerous to even party footsoldiers who worked tirelessly prior to the 2016 elections to support the party to win power.
Mr. Apor made the comment at the launch of the group at Kasoa in the Central Region.
He said some of these Ministers and other appointees never hit the ground to campaign ahead of the 2016 elections, but now enjoying the trappings of power while the footsoldiers struggle to make ends meet.
“As for house to house campaign, it’s our work as grassroots people, we are the people who do the grounds work. Those ministers none of them went to the villages to campaign, they were never slapped before like some of us were. But we who toiled for them to come to power they are not minding us. If you write a letter to an MP he’ll say I have nothing. But he is paid every month, the Minister is awarding contracts but when it is time to help the grassroots people then they will be complaining. We are the same people you’ll come to in 2020 asking us to go and do campaign.”
Mr Apor, however, added that the group will not stop doing the house to house campaign for the NPP to ensure the party retains power in 2020.


| Jump to DART Documentation Main Index |
dart_to_ncommas is the program that updates
a ncommas netCDF-format restart file (usually ncommas_restart.nc)
with the state information contained in a DART output/restart file
(e.g. perfect_ics, filter_ics, ... ).
Only the CURRENT values in the ncommas restart file will be updated.
The DART model time is compared to the time in the ncommas restart file.
If the last time in the restart file does not match the DART model time,
the program issues an error message and aborts.
From the user perspective, most of the time
dart_to_ncommas will be used on DART files that
have a header containing one time stamp followed by the model state.
The dart_to_ncommas_nml namelist allows
dart_to_ncommas to read the
assim_model_state_ic files that have
two timestamps in the header. These files are
temporarily generated when DART is used to advance the model.
One timestamp is the 'advance_to' time, the other is the 'valid_time'
of the model state. In this case, a namelist for ncommas (called
ncommas_in.DART) is written that contains the
&time_manager_nml settings appropriate to
advance ncommas to the time requested by DART. The repository version
of the advance_model.csh script has a section
to ensure the proper DART namelist settings for this case.
Conditions required for successful execution of dart_to_ncommas:
Since this program is called repeatedly for every ensemble member, we have found it convenient to link the DART input file to the default input filename (dart_restart). The same thing goes true for the ncommas output filename ncommas_restart.nc.
This namelist is read from the file input.nml. Namelists start with an ampersand '&' and terminate with a slash '/'. Character strings that contain a '/' must be enclosed in quotes to prevent them from prematurely terminating the namelist.
&model_nml ncommas_restart_filename = 'ncommas_restart.nc'; assimilation_period_days = 1, assimilation_period_seconds = 0, model_perturbation_amplitude = 0.2, output_state_vector = .true., calendar = 'Gregorian', debug = 0 /
&dart_to_ncommas_nml dart_to_ncommas_input_file = 'dart_restart', advance_time_present = .false. /
dart_to_ncommas_nml and model_nml are always read from a file called input.nml. The full description of the model_nml namelist is documented in the NCOMMAS model_mod.
| Item | Type | Description |
|---|---|---|
| dart_to_ncommas_input_file | character(len=128) | The name of the DART file containing the model state to insert into the ncommas restart file. |
| advance_time_present | logical | If you are converting a DART initial conditions or restart file this should be .false.; these files have a single timestamp describing the valid time of the model state. If .true. TWO timestamps are expected to be the DART file header. In this case, a namelist for ncommas (called ncommas_in.DART) is created that contains the &time_manager_nml settings appropriate to advance ncommas to the time requested by DART. |
ncommas_vars_nml is always read from a file called ncommas_vars.nml.
| Item | Type | Description |
|---|---|---|
| ncommas_state_variables | character(len=NF90_MAX_NAME) :: dimension(160) |
The list of variable names in the NCOMMAS restart file to use to create the DART state vector and their corresponding DART kind. |
&ncommas_vars_nml ncommas_state_variables = 'U', 'QTY_U_WIND_COMPONENT', 'V', 'QTY_V_WIND_COMPONENT', 'W', 'QTY_VERTICAL_VELOCITY', 'TH', 'QTY_POTENTIAL_TEMPERATURE', 'DBZ', 'QTY_RADAR_REFLECTIVITY', 'WZ', 'QTY_VERTICAL_VORTICITY', 'PI', 'QTY_EXNER_FUNCTION', 'QV', 'QTY_VAPOR_MIXING_RATIO', 'QC', 'QTY_CLOUDWATER_MIXING_RATIO', 'QR', 'QTY_RAINWATER_MIXING_RATIO', 'QI', 'QTY_ICE_MIXING_RATIO', 'QS', 'QTY_SNOW_MIXING_RATIO', 'QH', 'QTY_GRAUPEL_MIXING_RATIO' /
assim_model_mod location_mod model_mod null_mpi_utilities_mod obs_kind_mod random_seq_mod time_manager_mod types_mod utilities_mod
none
none - all error messages come from modules that have their own documentation.
none
None.
DART software - Copyright UCAR. This open source software is provided by UCAR, "as is", without charge, subject to all terms of use at http://www.image.ucar.edu/DAReS/DART/DART_download


Awork as a simple wrapper example. The code is
here.
Calculating next 10 Fibonacci numbers every 1 second


You have selected <% Modal.ini.name %> for initialling and signing. Please Confirm to proceed.
You have some unsaved Initials & Signatures which would get discarded before moving forward.


(dis'tild)
Premium Denim + Essentials.
No Retail Markup.
WE ALL BENEFIT FROM THE ABSENCE OF THE UNNECESSARY
LUXURY, REFINED
As our name suggests, we focus on simple design, superior quality, and a pared-down product selection in order to deliver the perfect core wardrobe. We’re inspired by understated, modern style and live by a fundamental, edited color palette: black, white, grey, and denim.
DIRECT TO YOU
We forgo middlemen (department stores and boutiques) to offer premium denim and luxury essentials at about 1/3 the traditional retail price. We don’t cut any corners – our products are manufactured in the same factories as notable designer labels.
MORAL FIBER
We demand a higher standard not just in our wardrobe, but also in labor practices and conditions. Whenever possible, we employ sustainable materials, natural dyes, and eco-friendly practices and techniques.
Team
Do stylish, high-quality garments require a luxury price tag? For DSTLD co-founders Corey Epstein and Mark Lynn,
the answer is a resounding no.
Epstein and Lynn have always valued a top-quality product and customer experience over
the name on the label of their clothes. But for two guys living in Los Angeles, the denim
capital of the world, they found it impossible to find well-made jeans and go-to essentials
without the premium price tag, so they took matters into their own hands.
Epstein, who’s diverse background includes photography, design, creative direction, and consulting, and Lynn, a luxury hospitality and e-commerce aficionado, knew they could build a brand that set them apart from traditional premium labels. A brand that was different, better, and had an edge. A brand for the modern consumer.
Their distinct vision and progressive platform made it easy to find a multi-talented crew of like-minded
individuals. Modest yet agile, the DSTLD team comes from some of the top brands and companies in the world:
GAP, John Varvatos, Adidas, Revolve, BCBG, Calvin Klein, Deloitte, and Caltech, to name a few. Most of us
left corporate culture to endure the even more demanding startup culture, and we love every minute of it.
We come from all over the globe, but call Los Angeles home.
DSTLD founders Corey Epstein (left) and Mark Lynn (right)


Solihull switches to 'Plan B' for town centre's underground heat network
Drilling earlier this year revealed that system won't be able to make use of water beneath Tudor Grange Park, with the council looking at an alternative plan using the same technology.
by David Irwin, https://www.facebook.com/David-Irwin-Local-Democracy-Reporter-792811574238027/?ref=settingsA multi-million pound plan to create an underground energy network in Solihull is still on the cards, although the original proposal to draw heat from water beneath Tudor Grange Park has been shelved.
Following borehole tests earlier this year, the council has confirmed that it would prove too difficult to return the water extracted from the aquifer - some 300 metres below the surface.
This means that officers now intend to look at using the same pump technology to draw heat from the air.
Despite the change of tack, it is still hoped that the first energy could be drawn from the new network - serving key town centre sites - in late 2022.
Last week, the Local Democracy Reporting Service (LDRS) sat down to discuss the latest developments with the project's key players and what the plan is going forward.
What work has been done to date?
Many passers-by will have seen the drilling equipment at Tudor Grange earlier in the year. This was used to create bore holes, extending down to the aquifer - a layer of water-bearing sandstone deep below ground.
Reaching the source took longer than expected because the aquifer was around 100 metres further down than initial surveys suggested. The exploratory work has since been completed.
What did the experts discover?
Ellie Horwitch-Smith, the heat network project manager, said that the temperature of the water was 18 degrees and tests showed a good flow. However, the findings suggested it would prove problematic returning the water extracted back to its underground source.
"It was a 50/50 chance really," she said. "You have to find out by drilling."
She explained that the extra infrastructure which would be needed meant that this set-up would pose problems from an "economic and practical perspective."
A key test of any system - and one which Friends of the Earth had highlighted last year - is that it doesn't expend more energy than it creates. This would undermine the entire aim of the project.
What is 'Plan B'?
The council is now looking at using the same heat pump technology but with "a different source" - drawing heat from the air. Crucially it is the source rather than the system which will differ.
While the water would have had a more constant temperature, the team insist that the air source option would be able to cope with colder periods of the year - based on the conditions over the course of 12 months.
Will this affect the current budget and timetable?
Ms Horwitch-Smith said it is still intended that "heat-on" happens towards the end of 2022. Updates are scheduled to go to a council scrutiny board in February and cabinet the following month.
All of the funding for investigations to date has been provided by the Department for Business, Energy and Industrial Strategy (BEIS) Heat Network Delivery Unit (HNDU) and the West Midlands Combined Authority. The first phase had previously been estimated at £604,800, while the overall capital budget remains at £11 million
What other factors might impact on plans?
The council has said that the network will need to take account of upcoming developments in the town centre, such as the planned Westgate project in Homer Road.
The new office block, expected to go to the planning committee in the coming months, is slap-bang in the middle of the area that the network is intended to serve.
The council has argued that, as with the HS2 development, it makes sense that projects are planned in tandem to avoid unnecessary disruption and expense after their completion
What work will need to be done?
The key element of the network will be the insulated pipes connecting up the buildings.
"It's just the construction required to lay pipes, the same as with other utilities," said Lisa Whitton, the UK Central project manager, when asked what the work would involve.
There will also be an energy centre built to house the equipment which keeps the network running. A number of sites are being considered for this base, which will need to go through the formal planning process.
A public consultation will be held, allowing discussion of the design.
What are the main benefits of the network?
Cllr Andy Mackiewicz, cabinet member for climate change, planning and housing, has previously said that the network will play a key role in the wider plans to make the borough more environmentally-friendly.
Since the plans were first made public last year, the council has committed to a target of becoming carbon neutral by 2030.
And of course the climate issue has come to increasing prominence in the past year, with protests both locally and nationwide dominating news bulletins and teenage activist Greta Thunberg becoming a household name.
This increased awareness has piled the pressures on councils, including Solihull, to take decisive action.
Ms Horwitch-Smith has emphasised that there are also "massive opportunities" from an educational perspective, particularly since schools and colleges are some of the public sector buildings which are set to be hooked up.
Work around the network recently saw workshops with students during last month's Earth Science Week.
How can I find out more?
The LDRS will be there for when the plans return to councillors in 2020. In the meantime residents can also sign-up to Stay Connected bulletins about the scheme - https://tinyurl.com/yxwqcwlq


I am Desire Kaleba, a Web Developer with strong commitments to collaboration and solutions-oriented problem-solving.
About meI am a Goal-oriented Web Developer with strong commitments to collaboration and solutions-oriented problem-solving.
I Use various web development tools ranking from frontend to backend to develop web applications and designs.
My commitments to high standards of web development, user experience and usability have made me a strong believer of a great web development temperament and experience to excel in my career.
Skills


High school football: Luther embracing challenge of facing defending champ Sperry
by Cameron JourdanLuther's matchup Friday is one of many great ones across Class 2A.
The Lions will travel to face No. 2 Sperry (11-0) in the second round of the playoffs. Other great matchups abound, but Luther (10-1) is the latest squad to get a shot at taking down the defending state champion.
Coach Shawn Meek said Sperry hasn't changed much in its philosophies from Week 1 to now. That's a large reason for their success and why the Pirates are again favorites to win the title.
For Luther, Meek said his team will have to control the ball and limit Sperry's ability to make big plays to come away with a victory.
"Sperry has a lot of athleticism," Meek said. "They've got some kids that can really go. We've got to limit the negative plays and put ourselves in manageable situations."
Related Photos


|
|
| RobotLogger (std::shared_ptr< robot_interfaces::RobotData< Action, Observation, Status >> robot_data, int block_size) |
| |
| std::vector< std::string > | get_header () |
| | To get the title of the log file, describing all the information that will be logged in it. More...
|
| |
| void | append_name_to_header (std::string identifier, std::vector< std::string > field_name, std::vector< std::vector< double >> field_data, std::vector< std::string > &header) |
| | Fills in the name information of each field to be logged according to the size of the field. More...
|
| |
|
void | append_header_to_file () |
| | Writes the header to the log file.
|
| |
|
void | append_robot_data_to_file () |
| | Writes the timestamped robot data at hopefully every time index to the log file.
|
| |
| void | append_field_data_to_file (std::vector< std::vector< double >> field_data) |
| | Appends the data corresponding to every field at the same time index to the log file. More...
|
| |
| void | write () |
| | Writes everything to the log file. More...
|
| |
| void | start (std::string filename) |
| | Call start() to create the thread for the RobotLogger and start logging! More...
|
| |
|
void | stop () |
| | Call stop() when you want to stop logging.
|
| |
template<typename Action, typename Observation, typename Status>
class robot_interfaces::RobotLogger< Action, Observation, Status >
To log data from any robot (real, simulated, fake).
The RobotLogger logs the timestamp, the time index, and the values of every Observation, Action, and Status variable. Observation, Action, and Status must derive from Loggable. Any further data structure can be logged similarly, which derives from Loggable.
- Template Parameters
-
| Action | |
| Observation | |
| Status | |
template<typename Action , typename Observation , typename Status >
This is to verify that the template types of the RobotLogger are based on Loggable.
Currently, the level of generalisability of the logger is that we know the following four timeseries structures exist for any robot whose data is to be logged- applied_action and desired_action (of type Action), observation (of type Observation), and status (of type Status).


Sharing Your Data
pyLabbook helps you share your data by sharing your labbook database files and protocol module files. The people you share your data with do not need to have pyLabbook to access your data.
Sharing Your Data With non-pyLabbook Users
pyLabbook wants you to be able to share your data freely and transparently. In fact, you can share your data with people that don’t even have pyLabbook installed.
Each one of your labbooks has a database file that contains your stored data. Transfer the data you want to share into a new labbook and share the new labbook’s database file.
The people you share your data with will need a sqlite database browser to read the database. Sqlite is one of the most widely used database formats and is heavily supported and developed. There are plenty of free and high quality options. We recommend SQLite Studio, which is cross-platform, self-contained and supports sqlite3.
Sharing Your Data With pyLabbook Users
For others to incorporate your data into their own pyLabbook system, you will need to provide them with:
- the data: a labbook’s database file containing the data you want to share.
- its structure: protocol modules for each protocol those data belong to.
Remember your protocol modules are in the python/pyLabbook/protocols
folder of your pyLabbook distribution.
That’s it! Send them those files and have them read the next section in this article about importing your data.
You do not need to send labbook modules because they will create a new labbook when importing your database.
Importing Shared Data
The protocol module file(s) can be copied into the protocol modules folder of their pyLabbook distribution (pyton/pyLabbook/protocols
) or they can use import the module(s) using the manager GUI protocol panel.
The database can be imported using the manager GUI when Creating a Labbook, or when creating a labbook using the Labbook Script. For an example of how to use the labbook script see the Basic Tutorial.
You can also overwrite the database of an existing labbook by copying the shared database file into databases/[LABBOOK_ID].sqlite3
of your pyLabbook distribution, where [LABBOOK_ID]
is the id/name of the labbook whose database you are overwriting.


I've made some 2D games in the past using graphics engines such as SDL and monogame but I wanted to try and make my own wrapper around OpenGL if I ever wanted to make something in 3D.
The current version of my wrapper can load different mesh file types such as .obj with .mtl and display them with a simple lighting system as well.
The following screenshots are from a scene I created in blender from free 3D assets which I then exported as .obj and loaded into my program.
This is the scene lit from above.
And this is the scene with lighting from the side, the source represented as the white cube.
There are currently no shadows which is a feature I would like to add in the future.
The code to generate the scene would look something like this:
int main()
{
Renderer renderer;
R_obj light_cube;
light_cube.load_model("C:\\Path\\to\\unit_cube.obj", false);
light_cube.set_world_location(glm::vec3(1.f, 1.f, 1.f));
light_cube.set_is_affected_by_lighting(false);
light_cube.build();
Point_light point_light;
point_light.set_world_location(glm::vec3(0.f, 1.f, 1.f));
point_light.set_ambient_color(glm::vec3(0.2f, 0.2f, 0.2f));
point_light.set_diffuse_color(glm::vec3(0.5f, 0.5f, 0.5f));
point_light.set_specular_color(glm::vec3(0.f, 0.f, 0.f));
point_light.set_attenuation_constants(Attenuation_constants(1.0, 0.0014, 0.000007));
Directional_light sun_light;
sun_light.set_ambient_color(glm::vec3(0.2f, 0.2f, 0.2f));
sun_light.set_diffuse_color(glm::vec3(0.5f, 0.5f, 0.5f));
sun_light.set_specular_color(glm::vec3(0, 0, 0));
sun_light.set_direction(glm::vec3(0, 0, -1.f));
R_obj scene;
scene.load_model("C:\\Path\\to\\scene.obj", false);
scene.set_is_affected_by_lighting(true);
scene.set_world_location(glm::vec3(0.f, 0.f, 0.f));
scene.build();
int loop_counter = 0;
while (!renderer.get_should_close_window())
{
loop_counter++;
renderer.add_render_object(&light_cube);
renderer.add_render_object(&scene);
glm::vec3 light_pos = glm::vec3(
0.f,
1.f + 50.f * cos((float)loop_counter/100.f),
1.f + 50.f * sin((float)loop_counter/100.f));
point_light.set_world_location(light_pos);
light_cube.set_world_location(light_pos);
renderer.add_light(&sun_light);
renderer.add_light(&point_light);
renderer.update();
}
renderer.clean_up();
return 0;
}


| summary.rlm {MASS} | R Documentation |
summary
method for objects of class "rlm"
## S3 method for class 'rlm' summary(object, method = c("XtX", "XtWX"), correlation = FALSE, ...)
object |
the fitted model.
This is assumed to be the result of some fit that produces
an object inheriting from the class |
method |
Should the weighted (by the IWLS weights) or unweighted cross-products matrix be used? |
correlation |
logical. Should correlations be computed (and printed)? |
... |
arguments passed to or from other methods. |
This function is a method for the generic function
summary()
for class "rlm"
.
It can be invoked by calling summary(x)
for an
object x
of the appropriate class, or directly by
calling summary.rlm(x)
regardless of the
class of the object.
If printing takes place, only a null value is returned.
Otherwise, a list is returned with the following components.
Printing always takes place if this function is invoked automatically
as a method for the summary
function.
correlation |
The computed correlation coefficient matrix for the coefficients in the model. |
cov.unscaled |
The unscaled covariance matrix; i.e, a matrix such that multiplying it by an estimate of the error variance produces an estimated covariance matrix for the coefficients. |
sigma |
The scale estimate. |
stddev |
A scale estimate used for the standard errors. |
df |
The number of degrees of freedom for the model and for residuals. |
coefficients |
A matrix with three columns, containing the coefficients, their standard errors and the corresponding t statistic. |
terms |
The terms object used in fitting this model. |
Venables, W. N. and Ripley, B. D. (2002) Modern Applied Statistics with S. Fourth edition. Springer.
summary(rlm(calls ~ year, data = phones, maxit = 50))


Doug La Malfa
CA - 01
Incumbent
Audrey Denny
CA - 01
Incumbent
Jared Hoffman
CA - 02
Incumbent
Dale Mensing
CA - 02
Incumbent
John Garamendi
CA - 03
Incumbent
Charlie Schaupp
CA - 03
Incumbent
Tom McClintock
CA - 04
Incumbent
Jessica Morse
CA - 04
Incumbent
Mike Thompson
CA - 05
Incumbent
Anthony Mills
CA - 05
Incumbent
Anthony Mills
CA - 05
Incumbent
Jrmar Mills
CA - 05
Incumbent


Woking 10 mile
Woking ENG
Race Winners
(34 runnings)
02 Apr
2006
49:45
1:01:55
03 Apr
2005
51:57
1:04:49
2004
---
---
30 Mar
2003
50:43
1:00:23
24 Mar
2002
50:20
59:41
2001
---
---
05 Mar
2000
47:58
57:54
07 Mar
1999
49:22
57:55
01 Mar
1998
49:30
54:30
02 Mar
1997
46:29
56:55
03 Mar
1996
48:25
55:52
05 Mar
1995
46:35
56:02
06 Mar
1994
48:09
55:20
07 Mar
1993
47:51
55:27
01 Mar
1992
47:44
56:18
03 Mar
1991
47:55
55:37
04 Mar
1990
49:04
57:08
26 Feb
1989
48:55
57:07
28 Feb
1988
49:03
55:15
08 Mar
1987
48:56
55:22
23 Feb
1986
49:18
55:10
24 Feb
1985
48:21
55:58
26 Feb
1984
48:20
57:28
27 Feb
1983
48:05
55:04
28 Feb
1982
48:10
56:45
28 Feb
1981
47:49
56:25
16 Feb
1980
48:44
1:04:04
24 Feb
1979
48:00
1:03:46
25 Feb
1978
48:02
26 Feb
1977
48:19
28 Feb
1976
47:48
08 Mar
1975
49:23
1974
n/a
24 Feb
1973
48:43
26 Feb
1972
48:17
27 Feb
1971
48:55
Notes: 1971 is believed to have been the inaugural year. Courses prior to 1980 are considered to have been short.
2006 was the final year for this race.
David Wardle (IRL)
Bel Levene (ENG)
Andrew Hunt (WAL)
Susanna Harrison (ENG)
not held
not held
Martin Rees (WAL)
Danielle Sanderson (ENG)
Michael Simpson (ENG)
Melanie Ellis (WAL)
not held
not held
Noel Cullen (IRL)
Sharon Dixon (ENG)
David Tune (ENG)
Frances Gill (WAL)
Nicholas Jones (ENG)
Alison Wyeth (ENG)
Richard Nerurkar-2
Lucia Subano (KEN)
Mark Flint (ENG)
Joanna Thompson-2
Richard Nerurkar (ENG)
Hayley Nash (WAL)
Christopher Buckley (WAL)
Joanna Thompson (ENG)
Peter Whitehead (ENG)
Susan Dilnot (ENG)
Philip Ellis (CAN)
Paula Fudge-2
Nigel Adams (WAL)
Paula Fudge (ENG)
Stephen Brace-3
Anne Roden (ENG)
Stephen Brace-2
Glynis Penny-2
Stephen Brace (WAL)
Karen Macleod (SCO)
Kevin O'Connor (ENG)
Sally James (WAL)
Graham Payne (ENG)
Julia Gates (ENG)
Keith Penny-2
Gillian Burley-Castka-2
Nick Sirs (ENG)
Gillian Burley-Castka (ENG)
Keith Penny (ENG)
Glynis Penny (ENG)
Michael Kearns (ENG)
Joanna Bennett (ENG)
Dennis Fowles (WAL)
Gillian Drake (ENG)
John Robertshaw (WAL)
Christine Stroud (ENG)
Paul Eales (ENG)
Barbara Burns (ENG)
Michael Critchley (WAL)
John King-2
John King (ENG)
Graeme Pringuer-4
Graeme Pringuer-3
Graeme Pringuer-2
Graeme Pringuer (ENG)
Steve Badgery (ENG)
Most Wins
(1971/date)
Men
3
Stephen Brace (WAL)
1988-90
Women
2
Gillian Burley-Castka (ENG)
1984-85
.
Glynis Penny (ENG)
1983,1989
.
Paula Fudge (ENG)
1991-92
.
Joanna Thompson (ENG)
1994,1996
Prize Money
(ADR qualified runners)
No information on prize money has been received for this race.

Last Updated on
27 Apr 2010
Contributor: Mick McGeoch (50)


Slider
A form control which lets the user specify a numeric value between a given range. Common use cases include configuring settings such as audio volume, color configuration, game difficulty etc.
Default slider
Default slider
Specifying minimum and maximum values
By default, the minimum is 0 and the
maximum is 100. You can specify different bounds using the
min
and/or max
attributes.
Setting granularity
By default, the value granularity is 1.
Change the step
attribute to control the
granularity. For example, If you need a value between 0 and 100, accurate
to 10% increments, you should set step="10"
.
If you need more granular control, the
step
attribute also accepts decimals.
If you want to accept any value
regardless of how many decimal places it extends to, specify a value of
any
for the step
attribute.
Disabled state
If a slider is currently unavailable for
some reason, you can apply a disabled state using the
is-disabled
class and the
disabled
attribute.


The Ecstasy of Gold: 5 Best Title Fights of the Weekend
by Luke Irwin
The championship fight. The pinnacle of achievement across combat sports for centuries. A premiere attraction that draws millions every year. But not all title bouts are created equally.
So which title bouts every week are the ones to watch? We’ll look over every title fight from across the combat sports landscape and give you the five best based on five criteria:
- Competitiveness: Is this an even matchup? Or just a warm body to throw at a champion? It’s a title fight, so we want the best possible at that division in that promotion.
- Excitement: How exciting will this fight be? A clash of two elite talents throwing everything they have at each other in an attempt to win the gold? Or a half-dead plod-fest devoid of action or risk?
- Juice: A sort of catch-all term for all the factors behind the matchup. Is there a story leading up to the match? A true rivalry? Anticipated rematch? Do the fighters dislike each other? Were the circumstances leading to the fight extraordinary, or was it just a promoter putting two names against each other? Is there a lot of excitement or hype going into it?
- Prestige: Applies to the belt itself, but also to the fighter wearing it. Is this a long-tenured champion defending? Is this an interim title or one that was vacated? Has the champion increased the prestige of the title or is this a fight that will increase the prestige of it?
- Viewing Ease: We all don’t mind suffering for our art (or hobbies), but sometimes paying twenty dollars for a choppy stream, or searching your cable plan for a channel you’re pretty sure was just invented three days ago in the 6000s isn’t the best of times. How easy, affordable, and stress-free is this bout to watch?
So here are your five best gold options for the weekend.
5. IBO/Interim WBA World Light Heavyweight Championships: Sven Fornling (c) (15-1) vs. Dominic Boesel (29-1)
When/Where: Saturday, 2:30pm, ESPN+
Competitiveness: 5
Excitement: 2
Juice: 1
Prestige: 3: As I always say, death to interim titles, ESPECIALLY one that already has TWO active, fighting champions under their banner. To the WBA’s credit, which I never say, they at least attempted to have a unification bout between Dmitry Bivol and Jean Pascal, before it fell apart due to Pascal’s withdrawing because of his father’s death.
Viewing Ease: 4: ESPN+ is really not optional if you’re a fight fan, anymore. Between the glut of UFC events, and a shitload of UK and European boxing, and Top Rank, which newly signed Naoya Inoue, the most exciting boxer in the world. C’mon, you have to sign up. It’s mandatory at this point.
Total: 15
4. Cage Fury Fighting Championship Featherweight Championship: Pat Sabatini (c) (10-2) vs. Mauro Chaulet (13-6)
When/Where: Saturday, 8:30pm, UFC Fight Pass
Competitiveness: 4: Sabatini is a Renzo Gracie fighter, and usually he’s able to overwhelm his opponents in CFFC with his submission game, but Chaulet is the rare fighter who’ll be up to his game.
Excitement: 4
Juice: 1
Prestige: 3: Somehow, Sabatini has been CFFC Featherweight champ for over two years. That never happens in regionals. Hell, even six months is a stretch.
Viewing Ease: 4
Total: 16
3. Commonwealth/BBBofC British Bantamweight Championships: Lee McGregor (7-0) vs. Ukashir Farooq (13-0)
When/Where: Saturday, 3:00pm, ESPN+
Competitiveness: 5: Both are undefeated, Scottish, and in their early-20s. You’ll hear these names a lot throughout the years.
Excitement: 3
Juice: 2
Prestige: 3: The Commonwealth and BBBofC British titles have been launching pads for waves of great UK boxers.
Viewing Ease: 4
Total: 17
t1. OneFC Flyweight Kickboxing Championship: Ilias Ennahaci (c) (30-3-1) vs. Wang Wenfeng (28-5-1)
When/Where: Saturday, 7:00am, OneFC App
Competitiveness: 5
Excitement: 2
Juice: 3: Ennahaci is making his first defense of his Flyweight title, and it’s against someone who defeated him in the Kunlun Fight Tournament quarterfinals a week over two years ago.
Prestige: 3: I think it’s pretty neat that ONE has both muay thai and kickboxing titles. Just enough difference and nuance to differentiate themselves from each other.
Viewing Ease: 5
Total: 18
t1. Inaugural OneFC Kickboxing Light Heavyweight Championship: Roman Kryklia (44-7) vs. Tarik Khbabez (46-5-1)
When/Where: Saturday, 7:00am, OneFC App
Competitiveness: 5
Excitement: 3
Juice: 3: These two are on a goddamned roll, winning their last 14 fights between the two of them. Nearly four years ago to the day, these two faced off in the SUPERKOMBAT World Grand Prix finals, with Khbabez taking a unanimous decision. One fighter is going to keep on their hot streak and either settle the score, or prove dominant over the other.

Total: 18


static
non-final
fields whose names are all in upper case.
Such fields may cause confusion by breaking a common naming convention and are often used by mistake.
Example:
public static int THE_ANSWER = 42; //a warning here: final modifier is missing
A quick-fix that renames such fields is available only in the editor.


HTMLTeXt
The idea of this project is to allow users with a web development background to write scientific papers using HTML instead of LaTeX by leveraging familiar elements like

,

and

. Then converting the content to a PDF.
The easiest way to get started is probably by checking out the examples.
You probably need a server running to use HTMLTeXt. You could, for example, check out Mozilla's testing server guide. Or if you are using VS Code you could use the extension Live Server to get livereload.
Features
HTMLTeXt currently supports the features I needed for writing my Master's thesis.
- Numbered headings
- Automatic table of contents
- Citing and generating bibliography from BibTeX file
- Footnotes
- Code highlighting
- Figure / Table numbering
- Internally referencing chapters and figures
- Abbreviations
- Splitting the content into pages
- Including content from other files
- + more
Generating PDF
- Open document in browser
- Open print dialog
- Save to file
Examples
Project Report
This project was started as a school project. The final report was written using HTMLTeXt.
HTMLTeX boilerplate
A minimal example that still showcases all of HTMLTeXt's features.
Browser support
Tested browsers:
| Chrome 66 |
Yes, +smallest generated PDF |
| Safari 11.1 |
Yes |
| Firefox 60 |
Slowest and buggy |
Troubleshooting
Have the browser console open to see if there are any errors or warnings
Error: Url: x.html not found!
: You possibly need to add /
to the end of your URL in the browser.


November
Toride Art Path
Tokyo University of the Arts, Ibaraki, Japan
GENESIS: Asia Network Beyond Design
Dream Forest Gallery, Seoul, South Korea
October
Embracing Borders: GAP Open Studio
Chinretsukan Gallery, Ueno, Tokyo, Japan
August
Geisai
Tokyo University of the Arts, Ueno, Tokyo, Japan


Fit linear and cox models regularized with net (L1 and Laplacian), elastic-net (L1 and L2) or lasso (L1) penalty, and their adaptive forms, such as adaptive lasso and net adjusting for signs of linked coefficients. In addition, it treats the number of non-zero coefficients as another tuning parameter and simultaneously selects with the regularization parameter. The package uses one-step coordinate descent algorithm and runs extremely fast by taking into account the sparsity structure of coefficients.
| Version: | 0.1 |
| Depends: | Matrix (≥ 1.2-3) |
| Imports: | Rcpp (≥ 0.12.2) |
| LinkingTo: | Rcpp, RcppEigen |
| Published: | 2015-12-12 |
| Author: | Xiang Li, Shanghong Xie, Donglin Zeng and Yuanjia Wang |
| Maintainer: | Xiang Li <xl2473 at cumc.columbia.edu> |
| License: | GPL-2 | GPL-3 [expanded from: GPL (≥ 2)] |
| NeedsCompilation: | yes |
| CRAN checks: | ADMMnet results |
| Reference manual: | ADMMnet.pdf |
| Package source: | ADMMnet_0.1.tar.gz |
| Windows binaries: | r-devel: ADMMnet_0.1.zip, r-release: ADMMnet_0.1.zip, r-oldrel: ADMMnet_0.1.zip |
| OS X binaries: | r-release: ADMMnet_0.1.tgz, r-oldrel: ADMMnet_0.1.tgz |
Please use the canonical form https://CRAN.R-project.org/package=ADMMnet to link to this page.


This is my attempt to build a [[https://retropie.org.uk/|Retropie]] console. The """original""" point here is the sound: I'm using a [[signal amplification (opamp)|HT28V739]] and made a nice box that should double as a nice speaker (hopefully).
Presentation
Principle
Just a retropie console, running on a Raspi 2 and with an opamp to drive a speaker, and cram everything in a wooden box that doubles up as a speaker enclosure.
But hey, why don't you use the GPIO pins in PWM mode instead of the audio jack?
Good question. 2 reasons:
* Don't want to change the Retropie config too much and just plugging the cable works fine. I'm lazy if you want.
* The PWM signal from the GPIO will not be 0v centered, basically we'd get the "upper" part of the wave only, so sound as is should be bad. (this is just my guess and I did not do any work to check, maybe 5 min of google would prove me wrong but I'm lazy right?)
Implementation
Bill of materials
* Raspberry pi 2
* HT28V739 op amp
* Speaker 8ohm
Schematics
Raspberry pi pinout:
* Official [[https://www.raspberrypi.org/documentation/usage/gpio/]]
* Sorry but clearer than official [[https://pinout.xyz/#]]
Source code
Pictures
Links
Helpful sources
Inspiration


Validation
DataMapper comes with built in validation, borrowing some of the existing functionality from the CodeIgniter Form Validation library. In fact, the validation is quite similar so you'll have no problems picking it up if you're already familiar with it. However, there are enough differences that you should read on to take full advantage of it!
Note: validate() is automatically run whenever you perform a save().
- Setting Validation Rules
- Setting Related Validation Rules
- Cascading Rules
- Custom Validation
- Custom Related Validation
- Predefined Validation Functions
- Predefined Related Validation Functions
- Error Messages
- Setting Custom Error Messages
- Changing the Error Delimiters
Setting Validation Rules
DataMapper lets you set as many validation rules as you need for a given field, cascading them in order, and it even lets you prep and pre-process the field data at the same time. Let's see it in action, we'll explain it afterwards.
Using the Basic Template from the DataMapper Models page, create a User model and add this code just above the class constructor:
var $validation = array( 'username' => array( 'label' => 'Username', 'rules' => array('required') ), 'password' => array( 'label' => 'Password', 'rules' => array('required') ), 'email' => array( 'label' => 'Email Address', 'rules' => array('required') ) );
Your model should now look like this:
<?php class User extends DataMapper { var $validation = array( 'username' => array( 'label' => 'Username', 'rules' => array('required') ), 'password' => array( 'label' => 'Password', 'rules' => array('required') ), 'email' => array( 'label' => 'Email Address', 'rules' => array('required') ) ); } /* End of file user.php */ /* Location: ./application/models/user.php */
In the above, we have specified that the username, password, and email fields are all required. When a developer attempts to save their user object to the database, these validation rules must be met in order for the save to be successful.
- array key - The field name in lowercase.
- label - The label you will give this field for use in error messages.
- rules - The validation rules the field value must pass in order to pass validation.
Also, you can add validation rules for non-Database Table fields, such as 'Confirm Email Address' or 'Confirm Password'. For example:
var $validation = array( 'username' => array( 'label' => 'Username', 'rules' => array('required') ), 'password' => array( 'label' => 'Password', 'rules' => array('required', 'encrypt') ), 'confirm_password' => array( // accessed via $this->confirm_password 'label' => 'Confirm Password', 'rules' => array('encrypt', 'matches' => 'password') ), 'email' => array( 'label' => 'Email Address', 'rules' => array('required', 'valid_email') ), 'confirm_email' => array( // accessed via $this->confirm_email 'label' => 'Confirm Email Address', 'rules' => array('matches' => 'email') ) );
Setting Related Validation Rules
DataMapper also lets you set validation rules for your relationships. Using save(), you can save both an object and its relationships at the same time. This is useful if you, for example, have a requirement that a User must relate to a Group. To validate this requirement, you would add rules for the Group relationship to the User $validation array in this way:
var $validation = array( 'username' => array( 'label' => 'Username', 'rules' => array('required') ), 'password' => array( 'label' => 'Password', 'rules' => array('required') ), 'email' => array( 'label' => 'Email Address', 'rules' => array('required') ), 'group' => array( 'label' => 'Group', 'rules' => array('required') ) );
Now, whenever you attempt to save a new User, you will only be able to successfully save it if you are also saving it with a Group relationship. If you are saving on an existing User, it will save if they are already related to a Group (otherwise you need to save with a Group relationship).
Cascading Rules
DataMapper lets you set multiple rules on each field. Let's try it. Change your $validation array like this:
var $validation = array( 'username' => array( 'label' => 'Username', 'rules' => array('required', 'trim', 'unique', 'min_length' => 3, 'max_length' => 20) ), 'password' => array( 'label' => 'Password', 'rules' => array('required', 'trim', 'min_length' => 3) ), 'email' => array( 'label' => 'Email Address', 'rules' => array('required', 'trim', 'unique', 'valid_email') ), 'group' => array( 'label' => 'Group', 'rules' => array('required') ) );
Now we have a mix of pre-processing and prepping validation functions.
Important: When cascading rules, note that rules are not run on empty fields unless the required or always_validate rules are set.
This includes anything that evaluates to TRUE for the empty() function, including: '', FALSE, or 0.
Pre-Processing
A pre-processing validation function is one that returns TRUE or FALSE depending on the field's value. For example, the required function checks if the field value is empty. If it is, it will return FALSE meaning the field value has not met the validation rule.
Prepping
A prepping validation function is one that directly modifies the value of the field. For example, trim will remove any leading or trailing whitespace from the field value.
Custom Validation
You can create custom validation functions specific to the DataMapper model you put it in. For example, here is an encrypt function which we'll put in our User model to encrypt the password.
Encrypt (prepping example)
// Validation prepping function to encrypt passwords function _encrypt($field) // optional second parameter is not used { // Don't encrypt an empty string if (!empty($this->{$field})) { // Generate a random salt if empty if (empty($this->salt)) { $this->salt = md5(uniqid(rand(), true)); } $this->{$field} = sha1($this->salt . $this->{$field}); } }
Where to Store Custom Validation Rules
Custom rules should be stored in one of two locations: either directly on the model itself, or in an extension class. The naming and usage rules are different depending on where you store them. You should always put rules that are used in multiple places in an extension class.
Rules
There are important rules you need to be aware of when setting up your custom validation functions.
For in-class rules:
- The function must be private and named in the format:
_
{rule}($field, $param = '') - The function must never be called directly.
- The first parameter contains the field name to be validated.
- The optional second parameter contains a setting that can be used by the function. Whether you use this depends upon your function. For example, the max_length function uses the second parameter as a number signifying the maximum length to validate the field against.
For extension-based rules:
- The function must be named in the format:
rule_
{rule}($object, $field, $param = '') - The first parameter contains the object being validated.
- The second parameter contains the field name to be validated.
- The optional third parameter contains a setting that can be used by the function. Whether you use this depends upon your function. For example, the max_length function uses the second parameter as a number signifying the maximum length to validate the field against.
For an example of an extension-based rule, scroll down to Exact Length
DataMapper's validate function ensures the validation rules are only applied to a field if it has changed since the last time validate ran. This prevents a field from having prepping functions applied to it multiple times, such as encryption, and the main reason why you should not call the actual validation functions directly. Calling an object's validate() function is all that's needed to have the validation rules applied.  You can also run or validate()->get() on an object to get a matching record using the objects current field values.
Anyway, back to putting in our custom encrypt function.
Add the encrypt function to your user model and the encrypt rule to the $validation array for the password field. Your model should now look like this:
<?php class User extends DataMapper { var $validation = array( array( 'field' => 'username', 'label' => 'Username', 'rules' => array('required', 'trim', 'unique', 'min_length' => 3, 'max_length' => 20) ), array( 'field' => 'password', 'label' => 'Password', 'rules' => array('required', 'trim', 'min_length' => 3, 'encrypt') ), array( 'field' => 'email', 'label' => 'Email Address', 'rules' => array('required', 'trim', 'unique', 'valid_email') ) ); function __construct($id = NULL) { parent::__construct($id); } // Validation prepping function to encrypt passwords function _encrypt($field) { // Don't encrypt an empty string if (!empty($this->{$field})) { // Generate a random salt if empty if (empty($this->salt)) { $this->salt = md5(uniqid(rand(), true)); } $this->{$field} = sha1($this->salt . $this->{$field}); } } } /* End of file user.php */ /* Location: ./application/models/user.php */
Now if you were to do the following:
$u = new User(); $u->username = "foo"; $u->password = "bar"; $u->save();
You would have a new user named foo saved to the database, with an encrypted password!
Exact Length (pre-processing example)
Here is an example of a custom pre-processing function using a parameter:
// Validation prepping function to encrypt passwords function _exact_length($field, $param) { // Check if field value is the required length if (strlen($this->{$field}) == $param) { return TRUE; } // Field value is not the required length return FALSE; }
And we would add it to the validation array like this:
$validation = array( 'word' => array( 'label' => 'Your Word', 'rules' => array('required', 'trim', 'exact_length' => 10) ) );
Now if word is not exactly 10 characters in length, it will fail validation.
Here is the same validation rule, but stored in an Extension Class:
class Custom_Rules { function __construct() { $CI =& get_instance(); // load in the custom rules language file. $CI->lang->load('custom_rules'); } // Validation prepping function to encrypt passwords function rule_exact_length($object, $field, $param) { // Check if field value is the required length if (strlen($object->{$field}) == $param) { return TRUE; } // Field value is not the required length return FALSE; } }
Note: The exact_length validation function is already included in DataMapper.
Custom Related Validation
You can create custom related validation functions specific to the DataMapper model you put it in. For example, here is a max_size function which we'll put in our Group model to restrict the size of each Group.
Max Size (pre-processing example)
// Checks if the value of a property is at most the maximum size. function _related_max_size($object, $model, $param = 0) { return ($this->_count_related($model, $object) > $size) ? FALSE : TRUE; }
Note: The max_size related validation function is already included in DataMapper.
Rules
There are important rules you need to be aware of when setting up your custom validation functions.
- The function must be private and named in the format:
_related_
{rule}($related_objects, $related_field, $param = '') - The function should never be called directly.
- The first parameter contains the related objects.
- The second parameter contains the related field name for the related object. (ie: 'user', 'creator', or 'editor')
- The optional third parameter contains a setting that can be used by the function. Whether you use this depends upon your function. For example, the max_size function uses the third parameter as a number signifying the maximum size to validate against.
Finally, you can also store related validation functions in an extension class, with the these rules:
- The function must be public and named in the format:
rule_related_
{rule}($object, $related_objects, $related_field, $param = '') - The first parameter contains the object being validated.
- The second parameter contains the related object.
- The third parameter contains the related field name for the related object. (ie: 'user', 'creator', or 'editor')
- The optional fourth parameter contains a setting that can be used by the function. Whether you use this depends upon your function. For example, the max_size function uses the third parameter as a number signifying the maximum size to validate against.
Predefined Validation Functions
DataMapper lets you use any of the validation functions in the CodeIgniter Form Validation library, as well as any native PHP function that accepts one parameter.
As well as those, DataMapper provides a few extra validation functions.
| Rule | Parameter | Description | Example |
|---|---|---|---|
| required | No | Returns TRUE if the field is not empty. | |
| always_validate | No | Does nothing, but notifies the validation routine to always run, even if the field is empty. | |
| alpha_dash_dot | No | Returns FALSE if the property contains anything other than alpha-numeric characters, underscores, dashes or full-stops. | |
| alpha_slash_dot | No | Returns FALSE if the property contains anything other than alpha-numeric characters, underscores, dashes, forward slashes or full-stops. | |
| boolean | No | Forces the propert to be TRUE or FALSE, using PHP's built-in boolean conversion. | |
| unique | No | Returns FALSE if the property is not unique. | |
| unique_pair | Yes | Returns FALSE if the property, paired with another property, is not unique. | 'unique_pair' => 'other_property' |
| min_size | Yes | Returns FALSE if the property is less than the specified size. | 'min_size' => 1 |
| max_size | Yes | Returns FALSE if the property is greater than the specified size. | 'max_size' => 10 |
| min_date | Yes | Returns FALSE if the property is less than the specified date. | 'min_date' => '1950-10-15' |
| max_date | Yes | Returns FALSE if the property is greater than the specified date. | 'max_date' => '2050-12-25' |
| valid_date | No | Returns FALSE if the property is not a valid date. | |
| valid_date_group | Yes | Returns FALSE if the property, grouped with other properties, is not a valid date. | 'valid_date_group' => array('year' => 'property1', 'month' => 'property2', 'day' => 'property3') |
| valid_match | Yes | Returns FALSE if the property does not match one of the specified array values. | 'valid_match' => array('value1', 'value2') |
Any custom validation functions you would like to add, can be added to your DataMapper models, such as the example of the encrypt function.
Predefined Related Validation Functions
DataMapper has some specific validation rules used to validate relationships. These are:
| Rule | Parameter | Description | Example |
|---|---|---|---|
| required | No | Returns FALSE if the object is not being saved with a relationship and one does not already exist. | |
| min_size | Yes | Returns FALSE if the number of relationships is less than the specified size. | 'min_size' => 1 |
| max_size | Yes | Returns FALSE if the number of relationships is greater than the specified size. | 'max_size' => 10 |
Any custom related validation functions you would like to add, can be added to your DataMapper models, such as the example of the max_size function above.
Error Messages
If any of the field values fail validation, the object will have its error property populated. You can view loop through and show each error in the error's all list, show the specific error for each field, or show all errors in one string. For example:
Viewing All Errors
foreach ($object->error->all as $e) { echo $e . "
"; }
Viewing Specific Field Errors
echo $object->error->fieldname; echo $object->error->otherfieldname;
Viewing All Errors as a Single String
echo $object->error->string;
The save function will return FALSE if validation fails, so if that happens you can check the error object for the errors.
Calling the validate() function will see a valid flag set to true or false. For example:
$this->validate(); if ($this->valid) { // Validation Passed } else { // Validation Failed }
Setting Custom Error Messages
With the option of creating custom validation functions or having custom methods specific to each DataMapper model, you'll at one time or another want to raise an error message. There are three ways to handle custom error message.
Using the error_message function
The most generic, which works from anywhere, is to use the error_message() method. This method accepts accepts two parameters.
$field - This is the name by which you'll access the error in the error object.
$error - This is the error message itself.
If you are using this from within a validation rule, don't return FALSE, as setting the error message is enough. Here is an example of setting a custom error message and accessing it.
$u = new User(); $u->error_message('custom', 'This is a custom error message.'); echo $u->error->custom;
Using Language Files
From within custom validation rules, you can return a FALSE value if an error occurs. If DMZ receives a FALSE value, it will attempt to look up the error based on the validation rule's name (ie: the min_size rule, stored under _min_size, needs a language string called min_size. This string will be passed into sprintf, with two string arguments, the field label and (if available) the rule's parameters.
For example, the min_size message looks like this:
$lang['min_size'] = 'The %s field must be at least %s.';
Which, with a parameter of 1 on the field user might render like this:
The User must be at least 1.
Returning Highly-Customized Messages
If you need to manipulate the error message more than the label and parameter, you can build the error message from within the custom validation rule, and return it instead of FALSE. It will still be passed to sprintf.
function _special_rule($field, $params) { $valid = ... // validate the field if( ! $valid) { $result = 'For your account, you can have no more than ' . $useraccount->max_widgets . ' widgets at a time.'; return $result; } }
Changing the Error Delimiters
By default, DataMapper adds a paragraph tag (
) around each individual error message. You can easily change these delimiters by setting the $error_prefix and $error_suffix class variables in your DataMapper model. For example, we'll set them in our User model:
1 2 3 4 5 6 7 8 • •<?php class User extends DataMapper { var $error_prefix = '
'; var $error_suffix = '
'; var $validation = array( [...]