packageDocumentation module import { PointProps } from "@itwin/appui-abstract" ; import { Point } from "./Point" ; import { Size , SizeProps } from "./Size" ; import { UiGeometry } from "./UiGeometry" ; public export interface RectangleProps { readonly left : number ; readonly top : number ; readonly right : number ; readonly bottom : number ; } internal export enum Corner { TopLeft , TopRight , BottomRight , BottomLeft } internal export class Rectangle implements RectangleProps { /** Creates rectangle from [[RectangleProps]]. */ public static create ( props ) { return new Rectangle ( props . left , props . top , props . right , props . bottom ) ; } /** Creates rectangle from [[SizeProps]]. */ public static createFromSize ( size ) { return new Rectangle ( 0 , 0 , size . width , size . height ) ; } /** Create a rectangle with 2 pairs of xy candidates. Theses are compared and shuffled as needed for the rectangle. */ public static createXYXY ( xA , yA , xB , yB ) { return new Rectangle ( Math . min ( xA , xB ) , Math . min ( yA , yB ) , Math . max ( xA , xB ) , Math . max ( yA , yB ) ) ; } /** Creates rectangle with specified bounds. */ public constructor ( public readonly left = 0 , public readonly top = 0 , public readonly right = 0 , public readonly bottom = 0 ) { } returns public getSize ( ) { const width = this . getWidth ( ) ; const height = this . getHeight ( ) ; return new Size ( width , height ) ; } returns public getWidth ( ) { return this . right - this . left ; } returns public getHeight ( ) { return this . bottom - this . top ; } returns public getCorner ( corner ) { switch ( corner ) { case Corner . TopLeft : { return this . topLeft ( ) ; } case Corner . TopRight : { return new Point ( this . right , this . top ) ; } case Corner . BottomLeft : { return new Point ( this . left , this . bottom ) ; } case Corner . BottomRight : { return new Point ( this . right , this . bottom ) ; } } } note returns public inset ( left , top , right , bottom ) { return new Rectangle ( this . left + left , this . top + top , this . right - right , this . bottom - bottom ) ; } returns public offset ( offset ) { return new Rectangle ( this . left + offset . x , this . top + offset . y , this . right + offset . x , this . bottom + offset . y ) ; } returns public offsetX ( offset ) { return new Rectangle ( this . left + offset , this . top , this . right + offset , this . bottom ) ; } returns public offsetY ( offset ) { return new Rectangle ( this . left , this . top + offset , this . right , this . bottom + offset ) ; } returns public setPosition ( position ) { return new Rectangle ( position . x , position . y , position . x + this . getWidth ( ) , position . y + this . getHeight ( ) ) ; } note returns public setHeight ( height ) { return new Rectangle ( this . left , this . top , this . right , this . top + height ) ; } note returns public setWidth ( width ) { return new Rectangle ( this . left , this . top , this . left + width , this . bottom ) ; } note returns public setSize ( size ) { return new Rectangle ( this . left , this . top , this . left + size . width , this . top + size . height ) ; } /** Checks if bounds of two rectangles match. */ public equals ( other ) { if ( this . left === other . left && this . top === other . top && this . right === other . right && this . bottom === other . bottom ) return true ; return false ; } note public containsPoint ( point ) { return point . x >= this . left && point . x <= this . right && point . y >= this . top && point . y <= this . bottom ; } note public containsXY ( x , y ) { return this . containsPoint ( { x , y } ) ; } returns note public contains ( other ) { return other . left >= this . left && other . right <= this . right && other . top >= this . top && other . bottom <= this . bottom ; } returns public containIn ( other ) { let contained = this . containVerticallyIn ( other ) ; contained = contained . containHorizontallyIn ( other ) ; return contained ; } returns public containVerticallyIn ( other ) { const contained = this . offsetY ( Math . min ( other . bottom - this . bottom , 0 ) ) ; return contained . offsetY ( Math . max ( other . top - contained . top , 0 ) ) ; } returns public containHorizontallyIn ( other ) { const contained = this . offsetX ( Math . min ( other . right - this . right , 0 ) ) ; return contained . offsetX ( Math . max ( other . left - contained . left , 0 ) ) ; } returns public topLeft ( ) { return new Point ( this . left , this . top ) ; } returns public center ( ) { const x = this . left + ( this . right - this . left ) / 2 ; const y = this . top + ( this . bottom - this . top ) / 2 ; return new Point ( x , y ) ; } returns public intersects ( other ) { return this . left < other . right && this . right > other . left && this . top < other . bottom && this . bottom > other . top ; } returns public outerMergeWith ( other ) { const left = Math . min ( this . left , other . left ) ; const top = Math . min ( this . top , other . top ) ; const right = Math . max ( this . right , other . right ) ; const bottom = Math . max ( this . bottom , other . bottom ) ; return new Rectangle ( left , top , right , bottom ) ; } returns public getVerticalSegmentBounds ( segmentId , numberOfSegments ) { const segmentHeight = this . getHeight ( ) / numberOfSegments ; const top = segmentId * segmentHeight ; return this . inset ( 0 , top , 0 , 0 ) . setHeight ( segmentHeight ) ; } returns public getHorizontalSegmentBounds ( segmentId , numberOfSegments ) { const segmentWidth = this . getWidth ( ) / numberOfSegments ; const left = segmentId * segmentWidth ; return this . inset ( left , 0 , 0 , 0 ) . setWidth ( segmentWidth ) ; } returns public getShortestDistanceToPoint ( point ) { let shortestDistance = 0 ; if ( point . x < this . left ) { if ( point . y < this . top ) shortestDistance = UiGeometry . hypotenuseXY ( this . left - point . x , this . top - point . y ) ; else if ( point . y <= this . bottom ) shortestDistance = this . left - point . x ; else shortestDistance = UiGeometry . hypotenuseXY ( this . left - point . x , this . bottom - point . y ) ; } else if ( point . x <= this . right ) { if ( point . y < this . top ) shortestDistance = this . top - point . y ; else if ( point . y <= this . bottom ) shortestDistance = 0 ; else shortestDistance = point . y - this . bottom ; } else { if ( point . y < this . top ) shortestDistance = UiGeometry . hypotenuseXY ( this . right - point . x , this . top - point . y ) ; else if ( point . y <= this . bottom ) shortestDistance = point . x - this . right ; else shortestDistance = UiGeometry . hypotenuseXY ( this . right - point . x , this . bottom - point . y ) ; } return shortestDistance ; } returns public toProps ( ) { return { bottom : this . bottom , left : this . left , right : this . right , top : this . top } ; } }