Есть ли способ правильно разместить строку текста в p5.js ?

#javascript #processing #p5.js

#javascript #обработка #p5.js

Вопрос:

Я много раз видел действительно классные примеры кинетической типографики. В этих примерах каждая буква является частицей. Текст представляет собой систему частиц, и на него могут воздействовать различные силы, такие как гравитация или даже центробежная сила. Эти системы изготавливаются в процессе обработки и в p5.js .

Я создаю интерактивный экран для Интернета, заполненный текстом, используя p5.js , вдохновленный этим примером кинетической типографики. Когда пользователь наводит курсор на текст, он начинает подпрыгивать по всему экрану.

Я перевел эскиз с обработки на p5.js и я заметил эту проблему, связанную с интервалом между текстом в функции setup(). При обработке код выглядит следующим образом, и он работает корректно.

Я хочу сосредоточиться на этом разделе кода обработки:

  void setup() {
 size(640, 360);
 //load the font
 f = createFont("Arial", fontS, true);
 textFont(f);
 // Create the array the same size as the String
 springs = new Spring[message.length()]; 
 // Initialize Letters (Springs) at the correct x location
 int locx = 40;
 //initialize Letters (Springs) at the correct y location
 int locy = 100;
  for (int i = 0; i < message.length(); i  ) {
  springs[i] = new Spring(locx, locy, 40, springs, i, message.charAt(i)); 
  locx  = textWidth(message.charAt(i));
   //boudaries of text just to make it a nice "go to head"
   if (locx >= 360) {
   locy =60;
   locx = 40;
   }
  }
}
 

Вы можете увидеть результат в этом изображении

Как вы можете видеть, параметр

    springs[i] = new Spring(locx, locy, 40, springs, i, message.charAt(i));    
   locx  = textWidth(message.charAt(i));
 

делает свое дело, расставляя буквы по интервалам.

Однако, когда я перевожу этот набросок в P5.js , Я не получаю такого же хорошего интервала. Это тот же раздел, но является p5.js код:

   function setup() {
  createCanvas(640, 360);
  noStroke();
  textAlign(LEFT);
  // Create the array the same size as the String
  springs = new Array(message.length);
  // Initialize Letters (Springs) at the correct x location
  var locx = 10;
  //initialize Letters (Springs) at the correct y location
  var locy = 120;
   for (var i = 0; i < message.length; i  ) {
   springs[i] = new Spring(locx, locy, 40, springs, i, message.charAt(i));
   locx  = textWidth(message.charAt(i));
   //boudaries of text just to make it a nice "go to head"
    if(locx>= 390){
    locy = 60;
    locx= 40;
    }
   }  
  }
 

Результат показывает

на этом изображении

Я уверен, что в коде p5js есть проблема, связанная с этой частью:

 springs[i] = new Spring(locx, locy, 40, springs, i, message.charAt(i));
locx  = textWidth(message.charAt(i));
 

Потому что я пытался исправить это, умножив значение locx, как показано здесь:

 springs[i] = new Spring(locx*5, locy, 40, springs, i, message.charAt(i));
 

Затем я получил

этот результат

что может показаться правильным, но я уверен, что это не так.

На данный момент я понятия не имею, как это исправить, это должно быть что-то вроде p5.js Я об этом не знаю. Любая помощь будет очень признательна.

// Редактировать, как предложено в комментарии, здесь вы можете найти класс Spring, написанный на p5.js:

     // Spring class
class Spring {
  constructor (_x, _y, _s, _others, _id, letter_) {
    // Screen values
    this.x_pos = this.tempxpos = _x;
    this.y_pos = this.tempypos = _y;
    this.size = _s;
    this.over = false;
    this.move = false;

    // Spring simulation constants
    this.mass =  8.0;       // Mass
    this.k = 0.2;    // Spring constant
    this.damp =0.98;       // Damping
    this.rest_posx = _x;  // Rest position X
    this.rest_posy = _y;  // Rest position Y

    // Spring simulation variables
    //float pos = 20.0; // Position
    this.velx = 0.0;   // X Velocity
    this.vely = 0.0;   // Y Velocity
    this.accel = 0;    // Acceleration
    this.force = 0;    // Force

    this.friends = _others;
    this.id = _id;

    this.letter = letter_;
    

  }
    update() {

      if (this.move) {
        this.rest_posy = mouseY;
        this.rest_posx = mouseX;
      }

      this.force = -this.k * (this.tempypos - this.rest_posy);  // f=-ky
      this.accel = this.force / this.mass;  // Set the acceleration, f=ma == a=f/m
      this.vely = this.damp * (this.vely   this.accel);         // Set the velocity
      this.tempypos = this.tempypos   this.vely;           // Updated position


      this.force = -this.k * (this.tempxpos - this.rest_posx);  // f=-ky
      this.accel = this.force / this.mass; // Set the acceleration, f=ma == a=f/m
      this.velx = this.damp * (this.velx   this.accel);  // Set the velocity
      this.tempxpos = this.tempxpos   this.velx; // Updated position


      if ((this.overEvent() || this.move) amp;amp; !(this.otherOver()) ) {
        this.over = true;
      } else {
        this.over = false;
      }
    }

    // Test to see if mouse is over this spring
    overEvent() {
      let disX = this.x_pos - mouseX;
      let disY = this.y_pos - mouseY;
      let dis = createVector(disX, disY);
      if (dis.mag() < this.size / 2 ) {
        return true;
      } else {
        return false;
      }
    }

    // Make sure no other springs are active
    otherOver() {
      for (let i = 0; i < message.length; i  ) {
        if (i != this.id) {
          if (this.friends[i].over == true) {
            this.velx = -this.velx;
            return true;
          }
        }
      }
      return false;
    }
    //the springs collides with the edges of the screen 
    box_collision() {
  if(this.tempxpos this.size/2>width){
  this.tempxpos = width-this.size/2;
  this.velx =  -this.velx;
  } else if (this.tempxpos - this.size/2 < 0){
  this.tempxpos = this.size/2;
  this.velx = -this.velx;
  }
  if (this.tempypos this.size/2>height) {
  this.tempypos = height-this.size/2;
  this.vely = -this.vely;
  } else if (this.tempypos- this.size/2 < 0) {
  this.tempypos = this.size/2;
  this.vely = -this.vely;
  }
}
    //the springs collides with each other
    collide() {
      for (var i = this.id   1; i < message.length; i  ) {

        var dx = this.friends[i].tempxpos - this.tempxpos;
        var dy = this.friends[i].tempypos - this.tempypos;
        var distance = sqrt(dx*dx   dy*dy);
        var minDist = this.friends[i].size/2   this.size/2;

        if (distance < minDist) { 
          var angle = atan2(dy, dx);
          var targetX = this.tempxpos   cos(angle) * minDist;
          var targetY = this.tempypos   sin(angle) * minDist;
          var ax = (targetX - this.friends[i].tempxpos) * 0.01;
          var ay = (targetY - this.friends[i].tempypos) * 0.01;
          this.velx -= ax;
          this.vely -= ay;
          this.friends[i].velx  = ax;
          this.friends[i].vely  = ay;
        }
      }
    }
  //display the letter Particle
    display() {
      if (this.over) {
        fill(255, 0, 0);
      } else {
        fill(255);
      }
      noStroke();
      textSize(fontS);
      //for debugging
      // ellipse(this.tempxpos, this.tempypos, this.size, this.size);
      text(this.letter, this.tempxpos, this.tempypos);
    }

    pressed() {
      if (this.over) {
        this.move = true;
      } else {
        this.move = false;
      }
    }

    released() {
      this.move = false;
      this.rest_posx = this.x_pos;
      this.rest_posy = this.y_pos;
    }
} 
 

И здесь вы можете найти ссылку на P5.js редактор с кодом:
Весенний текстовый код p5js

примечание: мне пришлось исправить класс Spring, потому что я не понимал, что все мои функции инициализируются в конструкторе. Теперь функции, составляющие класс, находятся вне конструктора. Я все еще не понял, как решить проблему с интервалом.

Комментарии:

1. Где Spring определен класс?

2. @Samathingamajig Класс определяется вне функций setup() и draw(). Это длинный фрагмент кода, если он может быть полезен для решения проблемы, я отредактирую этот пост.

3. Да, это очень важно. Кроме того, пожалуйста, добавьте для нас ссылку на веб-редактор p5 (но не удаляйте код из этого сообщения, просто добавьте эту ссылку в конце)

4. @Samathingamajig Я добавил класс Spring и ссылку на веб-редактор p5 с кодом.

Ответ №1:

Мне удалось решить проблему.

Насколько я понял, код был правильным с самого начала.

Что я пропустил во время путешествия, так это то, что мне нужно установить размер шрифта в функции setup(), если я хочу правильно отображать текст на экране.

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

Вы все равно можете увидеть результат, проверив ссылку на p5.js редактор, которого я опубликовал ранее.