Skip to content

Simplified celestial_pixel_scale (now re-named to proj_plane_pixel_scale) and new proj_plane_pixel_area - #3304

Merged
astrofrog merged 9 commits into
astropy:masterfrom
mcara:celestial_pixel_scale
Jan 21, 2015
Merged

astrofrog merged 9 commits into
astropy:masterfrom
mcara:celestial_pixel_scale

Conversation

@mcara

@mcara mcara commented Jan 16, 2015

Copy link
Copy Markdown
Contributor

This PR addresses issues raised in #3113 and #3230 related to celestial_pixel_scale.

I propose a simplified version of the celestial_pixel_scale that now will be called celestial_pixel_scales and will return a tuple of pixel scales for each axis. It is left to the user to decide how to use these scales. This function does not give any warnings about "non-square" pixels (the old function was really testing for the non-equilateral pixels). It is left to the user to test if pixels are "non-square", "non-equilateral", etc. (but see note below).

I also introduce a new function celestial_pixel_area that will compute pixel area. Square root of this area can be used to compute the pixel scale of an equivalent square pixel that has the same area as the area of the (generally non-square) pixel of the input WCS. This kind of quantity is better suitable for conversion of images from flux units to brightness than the arithmetic mean returned by the old celestial_pixel_scale as discussed in #3113.

NOTE: I plan to create a new PR with a function that can correctly test if a pixel is non-square.

NOTE: I have also removed the "Pixel sizes may very over the image..." warning as this is true for all projections except Cartesian (and that only when no distortions are present). Assuming in the future we will add (x,y) parameters to these two functions to compute pixel scales at various locations, this kind of warning may incur a severe (and unnecessary) performance penalty.

This PR addresses issues raised in #3113 and #3230 related to
`celestial_pixel_scale`.

I propose a simplified version of the `celestial_pixel_scale` that now
will be called `celestial_pixel_scales` and will return a tuple of
pixel scales for each axis. It is left to the user to decide how to use
these scales. This function does not give any warnings about
"non-square" pixels (the old function was really testing for the
**non-equilateral** pixels). It is left to the user to test if pixels
are "non-square", "non-equilateral", etc. (but see note below).

I also introduce a new function ``celestial_pixel_area`` that will
compute pixel area. Square root of this area can be used to compute the
pixel scale of an equivalent square pixel that has the same area as the
area of the (generally non-square) pixel of the input WCS. This kind of
quantity is better suitable for conversion of images from flux units to
brightness than the arithmetic mean returned by the old
`celestial_pixel_scale` as discussed in #3113.

NOTE: I plan to create a new PR with a function that can correctly test
is a pixel is non-square.

NOTE: I have also removed the "Pixel sizes may very over the image..."
warning as this is true for **all** projections except Cartesian (and
that only when no distortions are present). Assuming in the future we
will add (x,y) parameters to these two functions to compute pixel
scales at various locations, this kind of warning may incur a severe
(and unnecessary) performance penalty.
@mcara

mcara commented Jan 16, 2015

Copy link
Copy Markdown
Contributor Author

@astrofrog The tests should be passing, I believe... Travis failed probably because of some network error. I do not know what it wrong with AppVeyor.

EDIT: Just found the following message in AppVeyor: "Build execution time has reached the maximum allowed time for your plan (30 minutes)." So, I think the code is just fine but I do not know how to restart the tests.

@astrofrog

Copy link
Copy Markdown
Member

@mcara - thanks! I've restarted the tests.

@mcara

mcara commented Jan 16, 2015

Copy link
Copy Markdown
Contributor Author

@astrofrog AppVeyor still fails with message: "Build execution time has reached the maximum allowed time for your plan (30 minutes)." Is it possible to increase the allocated time for the test, or we just disregard this particular test?

Also, what you you think of the proposed changes? CC: @nden

@mcara

mcara commented Jan 16, 2015

Copy link
Copy Markdown
Contributor Author

I am ready to submit a new PR with a function that will test in a correct way if pixels are non-square (that is, if they contain distortions other than projection effects - projection effects are normally understood to be present with any kind of non-linear mapping, except Cartesian).

It would have been nice (=easier for me) if this PR was merged and then I would just modify the new master instead of an older version of the file. (I also understood from #3230 that there is some urgency in getting this done ASAP).

@astrofrog

Copy link
Copy Markdown
Member

I opened an issue with appveyor: http://help.appveyor.com/discussions/problems/1371-build-being-interrupted-after-30-minutes

In the mean time, maybe @keflavich (who wrote the original function) and @mdboom and/or @nden could review this?

@mcara - hopefully this will get merged in the next couple of days, so that you can open the other PR early next week.

@mcara mcara changed the title Simplified celestial_pixel_scales and celestial_pixel_area Simplified celestial_pixel_scale (now re-named to proj_plane_pixel_scale) and new proj_plane_pixel_area Jan 19, 2015
I think it is better if name of the functions indicates that the pixel
scales (pixel area) are computed in the projection plane from CD (PC,
CDELT) and not on the "celestial sphere" (as the old name might have
*suggested* - "celestial" in the old name was referring to "celestial
axes" as opposite to, e.g., spectral). This is to clearly indicated
that the computed scale *ignores* distortions due to non-linear nature
of most  projections.
@mcara

mcara commented Jan 19, 2015

Copy link
Copy Markdown
Contributor Author

I think it is better if name of the functions indicates that the pixel scales (pixel area) are computed in the projection plane from CD (PC, CDELT) and not on the "celestial sphere" (as the old name might have suggested - "celestial" in the old name was referring to "celestial axes" as opposite to, e.g., spectral). This is to clearly indicate that the computed scales ignore distortions due to non-linear nature of most projections.

Also, I have modified proj_plane_pixel_scales to compute the scales of the original input WCS and not of the astropy.wcs.WCS.celestial WCS object as it was done in the old celestial_pixel_scale. It seems to me that it is perfectly fine to compute the scale for non-celestial axes.

Comment thread astropy/wcs/utils.py Outdated

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is the float necessary here? The pixel scales are already guaranteed to be floats, no?

@keflavich

Copy link
Copy Markdown
Contributor

The PR seems fine to me, I just nitpicked one small thing. Of course, this PR removes the convenience function of deriving an approximate pixel scale, but the pixel area ought to be good enough.

The previous version also returned a Quantity. I think it's fine and sensible to return just a float and let users inspect the WCS to figure out what the units are.

Comment thread astropy/wcs/utils.py Outdated

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It may be better to write this as

return np.sqrt((wcs.pixel_scale_matrix**2).sum(axis=0, dtype=np.float))

@nden

nden commented Jan 20, 2015

Copy link
Copy Markdown
Contributor

My only use case involves using separate scales so I'm happy with the way this is written.

@mcara

mcara commented Jan 20, 2015

Copy link
Copy Markdown
Contributor Author

@nden your suggestion to return a numpy array is actually what I was thinking of doing (see my answer to @keflavich below). The reason I have used tuple(map(float,...)) was that when I was testing possible uses for the returned values, I got an error because the elements of the tuple were np.float64 (instead of Python floats) - I do not remember exactly how I got this (a few days ago) and I cannot reproduce it anymore.

@keflavich [Issue Nr. 1]: "Of course, this PR removes the convenience function of deriving an approximate pixel scale, but the pixel area ought to be good enough." It is true that this function removes the convenience factor, but it seems that (after discussing this with @nden and also by looking at various ways these scales are being used in the STScI software and Pyregion, etc.) there is no single good "average" pixel scale that is suitable for a large number of possible use cases. For this reason it seems better to let users decide what they want when they need a single number. It should be pretty easy to say proj_plane_pixel_scales(wcs).mean() if they need to, or sx,sy=proj_plane_pixel_scales(wcs) to get two scales as, e.g., @nden wants, etc.

I also thought that adding the which parameter (as well as allow_nonsquare) this early may hinder the ability to expand this function in the future. Specifically, I have the following "vision" (please forgive apparent but not intended grandioseness of the word "vision") for this function. At this moment we compute the scales and area only at CRPIX location ignoring SIP and table lookup distortions. However, in the future, I was thinking (assuming there will be interest in doing this) to add (x,y) parameters to this function to compute scales (area) at other locations in the image. Essentially, these two functions could be made to behave similarly to wcs.all_pix2world or wcs.pix2foc. That is, we could pass either arrays of [X], [Y] coordinates (arrays of length N), or arrays of form [[x1,y1],[x2,y2],...] of size Nx2. Adding such ability after the optional parameters which and allow_nonsquare, I think, will be difficult.

@keflavich [Issue Nr. 2]: "The previous version also returned a Quantity. I think it's fine and sensible to return just a float and let users inspect the WCS to figure out what the units are." Again it is true that I remove the "Quantity"/units from being returned. It seems fine to return a quantity for two scales (or a single pixel area). However, if in the future we will return an array of pixel areas and if this function will have input parameters (x,y) or just "xy", then it seems to me that it will be more difficult to deal with quantities for the following reasons:

  1. This function will behave differently from similar functions such as wcs.all_pix2world, wcs.pix2foc, etc. in the sense that it will return Quantities instead of values;
  2. Really, when (x,y) is provided then the units of x(y) will be important too. It is clear what to do when input units are 'pixels' but it is not clear to me what to do if units are 'mm', etc. Of course we can throw an exception if units are != 'pixels' - it is a solution. Except I do not think I have time to figure this out right now: I think it would be better to have some open discussion about this. However, if we do not want to replicate the behavior of wcs.all_pix2world or wcs.pix2foc then of course it is possible to return Quantities.

Please let me know if there is a strong desire to return Quantities and I can put them back (I do not have any strong opinion on this except that I think that by returning just values it allows more options for future expansion).

@mcara

mcara commented Jan 20, 2015

Copy link
Copy Markdown
Contributor Author

So, the vision (for the future) is that a function like proj_plane_pixel_area(wcs, x, y) could be used to produce "pixel area" maps.

@keflavich

Copy link
Copy Markdown
Contributor

@mcara - I'm happy with all the changes you made, I was just noting them. You have a reasonable idea of what this function is supposed to be; I had just implemented something that worked for one use case at the time. So, this is a resounding 👍 for the PR.

@mcara

mcara commented Jan 20, 2015

Copy link
Copy Markdown
Contributor Author

@keflavich Thank you very much for your comments! I really appreciate them and I just want to make clear that I do not have a "strong opinion" on how these functions should be (it is just my own "vision" based on my own limited experience) and I am really open to all suggestions as to how to make these functions more useful, clear, etc. to the users. Personally in my work I would use "pixel area" (and not "scale") so any suggestions/comments on "scale" are welcome... Except my understanding is that this should be done before the v1.0 release.

@mcara

mcara commented Jan 21, 2015

Copy link
Copy Markdown
Contributor Author

@astrofrog I have no idea what is wrong with the tests (travis): I have not even modified anything in the astropy/io/votable/tests/util_test.py or whatever test follows it, or why the following error appears in another failing test: ImportError: No module named 'pkg_resources'. AppVeyor test are being "queued" for half a day now...

I believe all tests should pass as they passed yesterday and the changes that I made to the code are too small to affect the tests.

@astrofrog

Copy link
Copy Markdown
Member

@mcara - I think the failures were unrelated indeed and I've restarted Travis.

@mcara

mcara commented Jan 21, 2015

Copy link
Copy Markdown
Contributor Author

@astrofrog @mdboom If anyone could merge this, then I would be able to create another PR for checking if pixels are non-square.

@astrofrog

Copy link
Copy Markdown
Member

This is great, thanks!

astrofrog added a commit that referenced this pull request Jan 21, 2015
Simplified celestial_pixel_scale (now re-named to proj_plane_pixel_scale) and new proj_plane_pixel_area
@astrofrog
astrofrog merged commit b6c606d into astropy:master Jan 21, 2015
@astrofrog astrofrog added this to the v1.0.0 milestone Jan 21, 2015
@astrofrog astrofrog added the wcs label Jan 21, 2015
@embray embray added the Affects-dev PRs and issues that do not impact an existing Astropy release label Jan 21, 2015
@embray

embray commented Jan 21, 2015

Copy link
Copy Markdown
Member

If I understand correctly I'm pretty sure this is affects-dev. But none of this work is mentioned in the changelog and I'm wondering if it should be, and to what extent. Are these new interfaces public, or just for internal use?

@embray

embray commented Jan 21, 2015

Copy link
Copy Markdown
Member

It seems the addition of celestial_pixel_scale was mentioned in the changelog, but now that it has been renamed that changelog entry should also be updated, and should include a link to this PR as well as the original one.

@astrofrog

Copy link
Copy Markdown
Member

Yes, this needs an updated changelog entry (i.e. we need to change the existing one). I'll do that.

@astrofrog

Copy link
Copy Markdown
Member

Done in a654376

@mcara

mcara commented Jan 22, 2015

Copy link
Copy Markdown
Contributor Author

The function that can perform a more complete check for pixels being non-square is proposed in #3329. Users can call that function to see whether pixels are non-square and then decide what to do about the two scales returned by proj_plane_pixel_scale.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Affects-dev PRs and issues that do not impact an existing Astropy release wcs

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants