Как увеличить область выделения объекта ткани?

Рассмотрим следующий код:

var lineObj = new fabric.Line([120,200,320,200],{
  stroke: '#000000',
  strokeWidth: 1
});
canvas.add(lineObj);

Эту линию в 1 пиксель очень сложно выделить из-за ее очень маленькой ширины. Что я хочу сделать здесь, так это увеличить область выбора. Как это:

Углы линии

Есть ли способ, которым я могу это сделать?


person Siddhant    schedule 13.03.2013    source источник
comment
Я не вижу никакого способа использовать API для увеличения размера ограничивающей рамки строки.   -  person markE    schedule 13.03.2013


Ответы (2)


Да, у нас есть значение padding для этого.

var lineObj = new fabric.Line([120,200,320,200], {
  stroke: '#000000',
  strokeWidth: 1,
  padding: 20
});
canvas.add(lineObj);

введите здесь описание изображения

Я упоминал, что Fabric является гибким и мощным? :)

@markE Хорошее решение! Рад, что вам легко пройтись по исходному коду.

person kangax    schedule 13.03.2013
comment
Абсолютно идеально! Это именно то, что мне нужно. Еще раз спасибо @kangax. - person Siddhant; 14.03.2013
comment
Гибкий и мощный... да. Легко найти нужный функционал... не всегда. Я работаю над этой проблемой в течение часа, пытаясь вручную настроить ограничивающую рамку и т. д. Отступы? Я бы не подумал об этом. Рад, что наконец нашел этот ответ. - person LarsH; 01.04.2016

Плохая новость – в API нет решения. Хорошие новости – вы можете закодировать свое решение.

API не предоставляет возможности расширить ограничивающую рамку линии, поэтому API не позволяет получить большую область выбора для линий.

FabricJS имеет открытый исходный код и хорошо организован, а сам исходный код содержит полезные комментарии. Вот что я нашел...

Объекты «Линия» расширяют объект «Объект». У «Объекта» есть вспомогательные методы, и наиболее подходящий из них находится в файле object_geometry.mixin.js. Там я обнаружил, что ограничивающая рамка для любого объекта создается с использованием метода getBoundingRect().

Вы спросили "Есть ли КАК-НИБУДЬ способ...", так вот:

Поэтому, чтобы решить вашу проблему, вы должны переопределить getBoundingRect() для строк и сделать его немного шире. Это автоматически сделает область выбора ваших линий шире, и на нее будет легче нажимать. @Kangax, не стесняйтесь указывать любое более простое решение!

Для начала вот исходный код getBoundingRect() из исходного файла object_geometry.mixin.js:

getBoundingRect: function() {
  this.oCoords || this.setCoords();

  var xCoords = [this.oCoords.tl.x, this.oCoords.tr.x, this.oCoords.br.x, this.oCoords.bl.x];
  var minX = fabric.util.array.min(xCoords);
  var maxX = fabric.util.array.max(xCoords);
  var width = Math.abs(minX - maxX);

  var yCoords = [this.oCoords.tl.y, this.oCoords.tr.y, this.oCoords.br.y, this.oCoords.bl.y];
  var minY = fabric.util.array.min(yCoords);
  var maxY = fabric.util.array.max(yCoords);
  var height = Math.abs(minY - maxY);

  return {
    left: minX,
    top: minY,
    width: width,
    height: height
  };
},

/**
 * Returns width of an object
 * @method getWidth
 * @return {Number} width value
 */
getWidth: function() {
  return this.width * this.scaleX;
},

/**
 * Returns height of an object
 * @method getHeight
 * @return {Number} height value
 */
getHeight: function() {
  return this.height * this.scaleY;
},

/**
 * Makes sure the scale is valid and modifies it if necessary
 * @private
 * @method _constrainScale
 * @param {Number} value
 * @return {Number}
 */
_constrainScale: function(value) {
  if (Math.abs(value) < this.minScaleLimit) {
    if (value < 0)
      return -this.minScaleLimit;
    else
      return this.minScaleLimit;
  }

  return value;
}
person markE    schedule 13.03.2013
comment
Я тоже внес изменения в файл Fabric.js, однако это повлияло на гибкость и простоту включения/отключения этой функции. Спасибо все равно @markE. - person Siddhant; 14.03.2013