I have a large triangle that is on top of a small rect. How can I select the rect without first moving the triangle out of the way.
I made a demo here:
https://codesandbox.io/s/w6wr7pmrx5
You need to enable perPixelTargetFind: true on your triangle so that the object's clickable area is determined by the actual object path rather than its bounding box.
http://fabricjs.com/docs/fabric.Object.html#perPixelTargetFind
Related
I can always check by looking at the co-ordinates and comparing with Image, of ellipse shape, but it fails when ellipse is at the corner.
I have tried using intersectWith method, it only works with bounding box, not the actual border of the shape.
This is the scenario I need it to work to be able to check if ellipse is outside of the background Image, not. bounding box.
There is a CTreeCtrl in an arbitrary position on a fixed size CDialog.
Could you please advice how to position this CTreeCtrl in OnInitDialog so that its left, right and bottom sides were touched to the dialog sides, and there was an indent N on top?
I've been experimenting for several hours now, but it doesn't stick correctly to right and bottom:
CRect rect;
GetWindowRect(&rect);
rect.top = N;
m_Tree.MoveWindow(&rect);
I also tried GetClientRect.
I need to get the following:
By far the easiest solution in this case it to just use the inbuilt Dynamic Layout functionality:
Select the control in the IDE.
Set the Sizing Type property to Both.
Set Sizing X and Sizing Y to 100.
Then, as long as your dialog Border property is set to Resizing the tree control will stretch as you wanted:
No coding required as you can see:
Much easier!
Manual Method
But, if you do things manually you need to be sure that you understand what type of coordinates the API calls provide you. Coordinates can be relative:
Screen Coordinates
Client Coordinates
For example:
CWnd::GetWindowRect:
The dimensions are given in screen coordinates relative to the upper-left corner of the display screen. The dimensions of the caption, border, and scroll bars, if present, are included.
CWnd::GetClientRect:
The client coordinates specify the upper-left and lower-right corners of the client area. Since client coordinates are relative to the upper-left corners of the CWnd client area, the coordinates of the upper-left corner are (0,0).
CWnd::MoveWindow:
For a top-level CWnd object, the x and y parameters are relative to the upper-left corner of the screen. For a child CWnd object, they are relative to the upper-left corner of the parent window's client area.
Your tree control is a child so when you move it, the coordinates need to be relative to the upper-left corner of the parent window's client area.
Note, there is a handy CWnd::ScreenToClient API to translate from one system to the other. But this is not required in this instance.
Manual Method — Example
Putting it all together:
CRect rct;
GetClientRect(&rct); // The client area of your window (in client coordinates)
rct.top += N; // Adjust the top margin as required
myTree.MoveWindow(&rct); // Now move the child control
Please note that I have not debugged this to verify the code but it conveys the ideas.
Where possible I use the built in dynamic resizing, althought it can be very tricky to work out the sizing values. But in your case it is simple - 100.
I should point out that the above code will manually get it to the right place. But then you have to resize it as the window resizes. Try the Dynamic Layout approach instead.
By default, the anchor for the text element in SVG is at the bottom left, but I want it to be at the top left, since I am also creating a rectangle to act as the background for the text, but it is displayed incorrectly since the text is higher than the rectangle (because rectangle anchor/offset is at the top left). Is there a way to fix this, so both text and rectangle can be drawn at same coordinates and be displayed in the same location.
The dominant-baseline property/attribute worked for me:
svg {
dominant-baseline: hanging;
}
The coordinates (x and y) you supply for text elements is used as the baseline of the text. This makes sense because if there is text with varying font sizes on the same line, you would want their baselines to line up.
There is no "automatic" way to do what you want. SVG elements are always absolutely positioned.
You will just have to move the text down a bit by making the y coordinate a bit larger.
Alternatively, you could add a dy attribute to shift the text down a bit. Or even use a transform attribute to do the same. But using either of those methods wouldn't really be simplifying the process for you.
In XAML there is the concept of a [Border] object that behaves much like an SVG rectangle except that a XAML [Border] can contain a child element.
So I could create a [Border] with a black stroke and inside it have another border that had a white stroke and a fill of Green.
This gives the the look of a single rectangle with both a black border & then an inner white border.
How can you create this in SVG?
You need multiple paths. In this particular case you could 'cheat' by having the same path twice, with the lower path having a larger border that appears 'outside' the upper object; in general, though you will need to create paths with offsets if you want this behavior.
This question already has answers here:
How can I cut one shape inside another?
(4 answers)
Closed 6 years ago.
So basically as my title says, I want to "cut a hole" in a rect element.
I have two rect elements, one on top of the other. The one on the bottom has a fill colour of white, and the one on the top has a fill colour of grey.
What I want to do is cut a triangle out of the top rect element so that the rect element below shows through.
This svg element is going to be used as an audio button for a media player on a page. In other words, you'll be able to click (or drag) your mouse left/right and the change in audio level will be represented by a change in the width of the rect element on the bottom, which shows through the triangle cut out of the top rect element.
I hope that's not too confusing. :P
Here is a quick mockup of what it should look like: http://forboden.com/coding/s1.png
Here is my code: http://forboden.com/coding/svgClipTest.html
Where am I going wrong here?
You should be able to use the fill-rule: evenodd(default) property to achieve this effect, if you want to prevent the fill of the rectangle from painting where the circle is. See this example from the SVG specification:
The key point is draw outer shape and inner shapes(holes) in different direction (clockwise vs anti-clockwise).
Draw the outer shape clockwise and draw the inner(holes) shapes anti-clockwise.
Or conversely, draw the outer shape(holes) anti-clockwise and draw the inner shapes clockwise.
Concat the path datas of outer shape and inner shapes(holes).
You can cut more holes by concat more hole path data.
This image explain how to cut a hole:
I see that you have it solved already, just wanted to add that if you want something more advanced then it's often quite easy to use a <mask>, see http://dev.w3.org/SVG/profiles/1.1F2/test/svg/masking-path-11-b.svg for example.
However, if you can avoid masking and clipping (e.g by just drawing things on top) that usually leads to better performance/user-experience.
Easiest way is to use <path> with the hole, and set pointer-events to none so events can pass through to the <rect> under. Of course there are many other ways to handle events such as wrapping them with a <g> and handling events on it.
You don't need to limit yourself to the basic shapes and use complicated clipping. Make things felxible enough so you can copy&paste path data generated by tools like inkscape.