Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/css/36.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Html 以百分比计算getBoundingClientRect_Html_Css_Angular_Getboundingclientrect - Fatal编程技术网

Html 以百分比计算getBoundingClientRect

Html 以百分比计算getBoundingClientRect,html,css,angular,getboundingclientrect,Html,Css,Angular,Getboundingclientrect,我已经在使用px中的子元素wrt到父元素的getBoundingClientRect()以及从一个组件到另一个组件的传递来计算左位置和顶部位置,并且能够将子元素放置在预期的位置上,但是我希望使子元素响应于父元素的wrt,因此我需要%中的左位置和顶部位置 我已经尝试过从控制台将px中的值和单位更改为%,并且能够获得所需的响应,但是尝试在代码中计算百分比并没有像预期的那样起作用,它没有将子元素放置在正确的位置,尽管实现了响应 minX: viewRect.left - movableClient

我已经在使用px中的子元素wrt到父元素的getBoundingClientRect()以及从一个组件到另一个组件的传递来计算左位置和顶部位置,并且能够将子元素放置在预期的位置上,但是我希望使子元素响应于父元素的wrt,因此我需要%中的左位置和顶部位置 我已经尝试过从控制台将px中的值和单位更改为%,并且能够获得所需的响应,但是尝试在代码中计算百分比并没有像预期的那样起作用,它没有将子元素放置在正确的位置,尽管实现了响应

  minX: viewRect.left - movableClientRect.left + movable.position.x,
  maxX: viewRect.right - movableClientRect.right + movable.position.x,
  minY: viewRect.top - movableClientRect.top + movable.position.y,
  maxY: viewRect.bottom - movableClientRect.bottom + movable.position.y

 this.dataService.setData(this.zonePosition = 
 {
  x : (viewRect.left - movableClientRect.left)/viewRect.left ,
  y: (viewRect.top - movableClientRect.top)/viewRect.top
  }
在前面的代码中,我只执行viewRect.left-movableClientRect.left,所以值是以像素为单位的,现在我尝试除以viewRect.left,然后再除以*100将其转换为%,但百分比值不能正确放置子元素

使用用于计算位置的指令进行更新

可移动指令 在这里,我计算子元素的x和y位置

interface Position {
  x: number;
  y: number;
}

@Directive({
 selector: '[appMovable]'
})
export class MovableDirective extends DraggableDirective {
@HostBinding('style.transform') get transform(): SafeStyle {
   return this.sanitizer.bypassSecurityTrustStyle(
  `translateX(${this.position.x}%) translateY(${this.position.y}%)`
  );
 }

 @HostBinding('class.movable') movable = true;

 position: Position = {x: 0, y: 0};
 zonePosition = {x:0, y:0, id:""}

 private startPosition: Position;

 @Input('appMovableReset') reset = false;

 constructor(private sanitizer: DomSanitizer, public element: ElementRef, 
  private dataService: DataService) {
  super(element);
  }

 @HostListener('dragStart', ['$event'])
  onDragStart(event: PointerEvent) {
   this.startPosition = {
     x: event.clientX - this.position.x,
     y: event.clientY - this.position.y
   }
 }

 @HostListener('dragMove', ['$event'])
  onDragMove(event: PointerEvent) {
   this.position.x = event.clientX - this.startPosition.x;
   this.position.y = event.clientY - this.startPosition.y;
  }

  @HostListener('dragEnd', ['$event'])
   onDragEnd(event: PointerEvent) {
    if (this.reset) {
     this.position = {x: 0, y: 0};
    }
   }
   }
我在其中计算子元素的左侧和顶部并将其分配给dataService的指令

  Directive({
   selector: '[appMovableArea]'
  })
  export class MovableAreaDirective implements AfterContentInit {
  @ContentChildren(MovableDirective) movables: QueryList<MovableDirective>;

  private boundaries: Boundaries;
  private subscriptions: Subscription[] = [];

  zonePosition = {x:0, y:0, id:""}

  constructor(private element: ElementRef, private dataService: DataService) 
  {}

  ngAfterContentInit(): void {
   this.movables.changes.subscribe(() => {
   this.subscriptions.forEach(s => s.unsubscribe());

   this.movables.forEach(movable => {
   this.subscriptions.push(movable.dragStart.subscribe(() => 
       this.measureBoundaries(movable)));
   this.subscriptions.push(movable.dragMove.subscribe(() => 
   this.maintainBoundaries(movable)));
   });
   });

   this.movables.notifyOnChanges();
    }

   private measureBoundaries(movable: MovableDirective) {
    const viewRect: ClientRect = 
       this.element.nativeElement.getBoundingClientRect();
    const movableClientRect: ClientRect = 
       movable.element.nativeElement.getBoundingClientRect();

    this.dataService.setData(this.zonePosition= {x : (viewRect.left - 
      movableClientRect.left)/viewRect.left , y: (viewRect.top - 
      movableClientRect.top)/viewRect.top, id: "" })

    this.boundaries = {
      minX: viewRect.left - movableClientRect.left + movable.position.x,
      maxX: viewRect.right - movableClientRect.right + movable.position.x,
      minY: viewRect.top - movableClientRect.top + movable.position.y,
      maxY: viewRect.bottom - movableClientRect.bottom + movable.position.y
    };
   }

    private maintainBoundaries(movable: MovableDirective) {
     movable.position.x = Math.max(this.boundaries.minX, 
      movable.position.x);
    movable.position.x = Math.min(this.boundaries.maxX, movable.position.x);
    movable.position.y = Math.max(this.boundaries.minY, movable.position.y);
    movable.position.y = Math.min(this.boundaries.maxY, movable.position.y);
   }
   }
指令({
选择器:“[appMovableArea]”
})
export类MovableArea指令在ContentInit之后实现{
@ContentChildren(MovableDirective)动产:QueryList;
私人边界:边界;
私人订阅:订阅[]=[];
zonePosition={x:0,y:0,id:“”
构造函数(私有元素:ElementRef,私有数据服务:数据服务)
{}
ngAfterContentInit():void{
此.movables.changes.subscribe(()=>{
this.subscriptions.forEach(s=>s.unsubscribe());
this.movables.forEach(movable=>{
this.subscriptions.push(movable.dragStart.subscripte(()=>
这是测量基础(可移动);
this.subscriptions.push(movable.dragMove.subscripte(()=>
这是(可移动的);
});
});
this.movables.notifyOnChanges();
}
专用计量基础(可移动:可移动指令){
const viewRect:ClientRect=
this.element.nativeElement.getBoundingClientRect();
常量movableClient:ClientRect=
movable.element.nativeElement.getBoundingClientRect();
this.dataService.setData(this.zonePosition={x:(viewRect.left-
movableCliert.left)/viewRect.left,y:(viewRect.top-
movableClientRect.top)/viewRect.top,id:“}”)
此值为0.1,边界={
minX:viewRect.left-movableClientRect.left+movable.position.x,
maxX:viewRect.right-movableClientRect.right+movable.position.x,
minY:viewRect.top-movableClientRect.top+movable.position.y,
maxY:viewRect.bottom-movableClientRect.bottom+movable.position.y
};
}
私有边界(可移动:可移动指令){
movable.position.x=Math.max(this.bounders.minX,
可移动(位置x);
movable.position.x=Math.min(this.bounders.maxX,movable.position.x);
movable.position.y=Math.max(this.bounders.minY,movable.position.y);
movable.position.y=Math.min(this.bounders.maxY,movable.position.y);
}
}

如果您已经拥有相对于容器元素的像素位置,则只需将px中的该值除以像素中容器的大小,然后将其乘以100:

perc_x = px_x / px_width * 100;
perc_y = px_y / px_height * 100;
elem=document.querySelector('.content');
container=document.querySelector('.container');
常数鼠标={
x:null,
y:空,
唐:错
};
让will_draw=false;
elem.onmousedown=e=>{
mouse.down=true;
};
onmouseup=e=>{
mouse.down=false;
};
document.onmousemove=e=>{
如果(!mouse.down){return;}
const container_rect=container.getBoundingClientRect();
//相对于容器,以px为单位
mouse.x=e.clientX-container_rect.left;
mouse.y=e.clientY-container_rect.top;
如果(!will_draw){
请求动画帧(绘制);
will_draw=true;
}
}
函数绘图(){
will_draw=false;
const{width,height}=container.getBoundingClientRect();
const perc_x=鼠标.x/宽度*100;
const perc_y=鼠标.y/高度*100;
//-5到中心(elem的宽度设置为10%)
elem.style.setProperty('left',(perc_x-5)+'%');
//-5到中心(elem的高度设置为10%)
elem.style.setProperty('top',(perc_y-5)+'%');
}
.container{
宽度:80vw;
高度:80vh;
边框:1px实心;
位置:相对位置;
}
.内容{
宽度:10%;
身高:10%;
位置:绝对位置;
最高:45%;
左:45%;
背景:绿色;
}

如果您已经拥有相对于容器元素的像素位置,则只需将px中的该值除以像素中容器的大小,然后将其乘以100:

perc_x = px_x / px_width * 100;
perc_y = px_y / px_height * 100;
elem=document.querySelector('.content');
container=document.querySelector('.container');
常数鼠标={
x:null,
y:空,
唐:错
};
让will_draw=false;
elem.onmousedown=e=>{
mouse.down=true;
};
onmouseup=e=>{
mouse.down=false;
};
document.onmousemove=e=>{
如果(!mouse.down){return;}
const container_rect=container.getBoundingClientRect();
//相对于容器,以px为单位
mouse.x=e.clientX-container_rect.left;
mouse.y=e.clientY-container_rect.top;
如果(!will_draw){
请求动画帧(绘制);
will_draw=true;
}
}
函数绘图(){
will_draw=false;
const{width,height}=container.getBoundingClientRect();
const perc_x=鼠标.x/宽度*100;
const perc_y=鼠标.y/高度*100;
//-5到中心(elem的宽度设置为10%)
elem.style.setProperty('left',(perc_x-5)+'%');
//-5到中心(elem的高度设置为10%)
elem.style.setProperty('top',(perc_y-5)+'%');
}
.container{
宽度:80vw;
高度:80vh;
边框:1px实心;
位置:相对位置;
}
.内容{
宽度:10%;
身高:10%;
位置:绝对位置;
最高:45%;
左:45%;
背景:绿色;