[FTUI3] bugs im ftui-swiper

Begonnen von Jones, 20 Juli 2023, 11:48:49

Vorheriges Thema - Nächstes Thema

Jones

- next() / back() setzt auto-play intervall nicht zurück, so kann es passieren, das der dot beim click 2 positionen weiter springt.
  lösung: bis zum fix checkIntervall() hinzufügen: @click="swiper1.next();swiper1.checkInterval();"

- chrome hat keine probleme, aber firefox zeigt immer eine horizontale scrollbar an.
  brute force lösung: in swiper.component.css -> .slides -> overflow-x: hidden;
  (meiner meinung nacht macht bei einem swiper eine scrollbar für den text eh keinen sinn)

- wenn readings "wegfallen" springt der dot mehrfach hin und her.
  (ist mir aufgefallen bei "FTUI3 Proplanta Wetter" aus dem wiki, nachdem in uwz eine der 3 warnungen aufgehoben wurde)

[update 28.08.23]: zusammenfassung zum aktuellen stand
die verbesserungen von mr_petz für die .js
/*
* Swiper component for FTUI version 3
*
* Copyright (c) 2021-2022 Mario Stephan <mstephan@shared-files.de>
* Under MIT License (http://www.opensource.org/licenses/mit-license.php)
*
* https://github.com/knowthelist/ftui
*/

import { FtuiElement } from '../element.component.js';
import { createElement } from '../../modules/ftui/ftui.helper.js';

class FtuiSwiper extends FtuiElement {

  constructor(properties) {

    super(Object.assign(FtuiSwiper.properties, properties));
    this.currentIndex = 0;
    this.tempIndex = 0;
    this.container = this.shadowRoot.querySelector('.slides');
    this.slotMain = this.shadowRoot.querySelector('slot');
    this.slotDots = this.shadowRoot.querySelector('slot[name=dots]');
    const supportTouch = 'ontouchstart' in document;
    this.container.addEventListener((supportTouch ? 'scroll' : 'mouseleave'), e => this.doScroll(e,supportTouch));
  }


  template() {
    return `
      <style> @import "components/swiper/swiper.component.css"; </style>
      <div class="slides">
        <slot></slot>
      </div>
      <slot name="dots"></slot>
      `;
  }

  static get properties() {
    return {
      value: '',
      debounce: 200,
      dots: false,
      autoPlay: false,
      interval: 5,
    };
  }

  static get observedAttributes() {
    return [...this.convertToAttributes(FtuiSwiper.properties), ...super.observedAttributes];
  }

  get slides() {
    return this.slotMain.assignedElements();
  }

  onConnected() {
    this.createDots();
    this.checkInterval();
    this.initObservers();
  }

  initObservers() {
    this.slides.forEach(item => this.initInViewportObserver(item));
    this.slides.forEach(item => this.initMutationObserver(item));
  }

  initInViewportObserver(elem) {
    const observer = new IntersectionObserver(
      this.onIntersectionChange.bind(this),
      {
        root: this.container,
        delay: 100,
        trackVisibility: true,
      });
    observer.observe(elem);
  }

  initMutationObserver(elem) {
    const observer = new MutationObserver(
      this.onMutations.bind(this));
    observer.observe(elem,
      {
        attributes: true,
        attributeFilter: ['hidden'],
      });
  }

  onIntersectionChange(entries) {
    if (!this.autoPlay) {
      entries.forEach(entry => {
        entry.target.isVisible = ('isVisible' in entry) ? entry.isVisible : entry.isIntersecting;
        if (entry.target.isVisible && this.value !== entry.target.id) {
          this.submitChange('value', this.value);
        }
      });
    }
  }

  // refresh if a slide changes visibility
  onMutations(entries) {
    entries.forEach(() => {
      this.updateDots();
      this.next();
    });
  }

  onAttributeChanged(name, newValue, oldValue) {
    switch (name) {
      case 'value': {
        if (newValue !== oldValue) {
          const target = this.slides.find(item => item.id === newValue);
          this.currentIndex = this.slides.indexOf(target);
          this.updateDots();
          if (target) {
           this.tempIndex < this.currentIndex && this.currentIndex !== this.slides.length-1 ? this.tempIndex++ : this.slides[0].style.display === 'none' ? this.tempIndex = 0 : this.tempIndex = this.currentIndex;
           this.container.scrollTo({left: (target.offsetWidth+50)*(this.tempIndex !== this.currentIndex ? this.tempIndex : this.currentIndex), behavior: 'smooth'});
          }
        }
      }
        break;
      case 'interval':
      case 'auto-play':
        this.checkInterval();
        break;
    }
  }

  doScroll(e,supportTouch) {
   const ePos = Math.ceil((e.target.scrollLeft+e.target.offsetLeft)/10)*10;
   for(let i = 0; i < this.slides.length; i++){
    const slidePos = Math.ceil((this.slides[i].offsetLeft)/10)*10;
    if (slidePos === ePos || slidePos+10 === ePos || slidePos-10 === ePos) {
     this.tempIndex = i;
     this.currentIndex = i;
     supportTouch ? '' : this.submitChange('value', this.slides[this.currentIndex].id);
    }
   }
  }

  onDotClicked(event) {
    this.setValueByIndex(event.target.id.replace(`${this.id}-dot-`, ''));
  }

  back(iteration = 1) {
    this.currentIndex--;
    if (this.currentIndex < 0) {
      this.currentIndex = this.slides.length - 1;
    }
    // if previous slide is hidden, get the next one
    if (this.slides[this.currentIndex].hidden && iteration < this.slides.length) {
      this.back(iteration++);
    } else {
      if (iteration === this.slides.length) {
        this.currentIndex = -1;
        this.updateDots();
      }
      this.setValueByIndex(this.currentIndex);
    }
  }

  next(iteration = 0) {
    this.currentIndex++;
    if (this.currentIndex >= this.slides.length) {
      this.currentIndex = 0;
    }
    // if next slide is hidden, get the next one

    if (this.slides[this.currentIndex].hidden && iteration < this.slides.length) {
      iteration++;
      this.next(iteration);
    } else {
      if (iteration === this.slides.length) {
        this.currentIndex = -1;
        this.updateDots();
      }
      this.setValueByIndex(this.currentIndex);
    }
  }

  setValueByIndex(index) {
    const slide = this.slides[index];
    if (slide) {
      this.submitChange('value', slide.id);
    }
  }

  createDots() {
    if (this.slotDots.assignedElements().length > 0 || !this.dots) {
      return;
    }
    this.slides.forEach((item, index) => {
      const elem = createElement('div', 'dot');
      elem.addEventListener('click', this.onDotClicked.bind(this));
      if (item.id === this.value) {
        elem.classList.add('active');
      }
      elem.id = `${this.id}-dot-${index}`;
      this.slotDots.appendChild(elem);
    })
  }

  updateDots() {
    const dotElements = this.slotDots.assignedElements().length
      ? this.slotDots.assignedElements() : this.slotDots.childNodes;
    dotElements.forEach((dotElement, index) => {
      dotElement.classList.toggle('hidden', this.slides[index].hidden);
      if (this.currentIndex === index) {
        dotElement.classList.add('active');
      } else {
        dotElement.classList.remove('active');
      }
    });
  }

  checkInterval() {
    clearInterval(this.intervalTimer);
    if (this.interval && this.autoPlay) {
      this.intervalTimer = setInterval(() => this.next(), this.interval * 1000);
    }
  }

}

window.customElements.define('ftui-swiper', FtuiSwiper);


und meine verbesserungen für die .css
:host {
  width: 100%;
  height: 100%;
  text-align: center;
  overflow: hidden;
}

.slides {
  display: flex;
  overflow-x: scroll;
  scroll-snap-type: x mandatory;
  scroll-behavior: smooth;
  -webkit-overflow-scrolling: touch;
  z-index: 0;
  height: 100%;
}

:host([dots]) .slides {
  height: calc(100% - 1em);
}

.slides::-webkit-scrollbar {
  width: 10px;
  height: 10px;
}

/* Firefox */
:host(:not([scrollbar])) .slides {
  scrollbar-width: none;
}

.slides {
  scrollbar-color: var(--swiper-scrollbar-thumb) var(--swiper-scrollbar-track);
}

/* All but Firefox */
:host(:not([scrollbar])) .slides::-webkit-scrollbar {
  width: 0;
  height: 0;
}

.slides::-webkit-scrollbar-thumb {
  background: var(--swiper-scrollbar-thumb);
  border-radius: 10px;
}

.slides::-webkit-scrollbar-track {
  background: var(--swiper-scrollbar-track);
}

slot[name=dots] {
  display: flex;
  align-items: center;
  justify-content: center;
}

.dot {
  height: 0.5em;
  width: 0.5em;
  margin-left: 0.5em;
  border-radius: 1em;
  background-color: var(--swiper-dot);
  cursor: pointer;
}

.dot.active {
  background-color: var(--swiper-dot-active);
}

.dot.hidden {
  display: none;
}

::slotted(*) {
  scroll-snap-align: start;
  flex-shrink: 0;
  width: 100%;
  height: 100%;
  margin-right: 50px;
  border-radius: 10px;
  transform-origin: center center;
  transition: transform 0.5s;
  display: flex;
  justify-content: space-evenly;
  align-items: center;
  flex-direction: column;
}

sind noch so einige baustellen vorhanden, aber ich hatte die letzten tage keine kaputte anzeige mehr
und der firefox verhält sich jetzt wie chrome beim fehlen vom scrollbar parameter.



[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

mr_petz

Ist bekannt.
Schau dir das an mit einem Lösungsvorschlag von mir:
https://forum.fhem.de/index.php?topic=115259.3285

Eine Seite davor steht auch noch was dazu.

LG

Jones

sry, hatte gedacht das ist alles schon eingepflegt weil das posting vom märz war.

werde mir definitiv deine fixes ansehen, weil ich mich nämlich nächste woche an der visualisierung von uwz versuchen werde. mit der ftui3 uwz demo aus dem wiki bin ich nämlich nicht zufrieden.
in ftui2 habe ich die warnmeldungen instant erhalten, in der demo mit ein paar stunden verzögerung. außerdem hat das grüne (orange war ok, rot nicht getestet) warndreieck ne andere farbe wie der hintergrund.
und der swiper hatte in der demo die oben genannten probleme.

[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

yersinia

Zitat von: mr_petz am 20 Juli 2023, 18:03:22Ist bekannt.
Schau dir das an mit einem Lösungsvorschlag von mir:
https://forum.fhem.de/index.php?topic=115259.3285

Eine Seite davor steht auch noch was dazu.
Welche von den zwei js ist denn die aktuellere? ;)

Ansonsten kann ich dafür nen pr aufmachen - die letzte Änderung an der swiper component ist schon was her...
viele Grüße, yersinia
----
FHEM 6.4 (SVN) on RPi 4B with RasPi OS Bookworm (perl 5.36.0) | FTUI
nanoCUL->2x868(1x ser2net)@tsculfw, 1x433@Sduino | MQTT2 | Tasmota | ESPEasy
VCCU->14xSEC-SCo, 7xCC-RT-DN, 5xLC-Bl1PBU-FM, 3xTC-IT-WM-W-EU, 1xPB-2-WM55, 1xLC-Sw1PBU-FM, 1xES-PMSw1-Pl

mr_petz

Hi yersinia,
das war alles zum testen gedacht. Hatte sich leider (wie so oft) nur einer gemeldet ob es besser so funktioniert.
Ist halt schade dass man hier zuwenig Rückmeldung bekommt. Wenn nichts kommt lass ich es sein und gehe der Sache nicht weiter auf den Grund...
Ich habe die letzte Version jetzt nur noch im Post stehen. Die andere würde unter Umständen auch gehen.
Ein PR würde ich lassen, da sich auch setstate dazu nicht geäußert hat...

LG

yersinia

#5
Zitat von: mr_petz am 21 Juli 2023, 07:54:06Hatte sich leider (wie so oft) nur einer gemeldet ob es besser so funktioniert.
Ist halt schade dass man hier zuwenig Rückmeldung bekommt. Wenn nichts kommt lass ich es sein und gehe der Sache nicht weiter auf den Grund...
Verständlich. Allerdings stellt sich die Frage ob setstate wirklich immer den Überblick behält in dem Monsterthread. Ein pr ist da vlt ein geeignetes Mittel um ihn 'aktiver' drauf zu stubsen - übernehmen muss er den pr ja nicht. Aber deine Beweggründe kann ich voll und ganz nachvollziehen.
viele Grüße, yersinia
----
FHEM 6.4 (SVN) on RPi 4B with RasPi OS Bookworm (perl 5.36.0) | FTUI
nanoCUL->2x868(1x ser2net)@tsculfw, 1x433@Sduino | MQTT2 | Tasmota | ESPEasy
VCCU->14xSEC-SCo, 7xCC-RT-DN, 5xLC-Bl1PBU-FM, 3xTC-IT-WM-W-EU, 1xPB-2-WM55, 1xLC-Sw1PBU-FM, 1xES-PMSw1-Pl

mr_petz

Haste auch Recht.
Ich möchte halt erst einen Feldtest und dan einchecken...

LG

Jones

@mr_petz
habe deine swiper version aus dem endlosthread mit folgender config getestet:
<ftui-grid-tile row="1" col="6" height="4" width="5">
      <ftui-swiper id="swiper" height="300px;" @click="swiper.next(); " intervall="2" auto-play dots >
        <ftui-icon id="sw2_1" name="washing-machine" size="6"></ftui-icon>
        <ftui-icon id="sw2_2" name="garage-variant" size="6"></ftui-icon>
        <ftui-icon id="sw2_3" name="car-battery" size="6"></ftui-icon>
        <ftui-icon id="sw2_4" name="mower" size="6"></ftui-icon>
        <ftui-icon id="sw2_5" name="projector" size="6"></ftui-icon>
      </ftui-swiper>
</ftui-grid>

erledigt:
- kein "rumgezappel" mehr.
- dots anklicken und swiper scrollt an die entsprechende stelle funktioniert jetzt zuverlässig.
  (wenn @click nicht genutzt wird, was bei funktionierendem swiper ja der fall wäre).

noch offen:
- dieser störende scrollbalken wird im ff immer angezeigt, chrome hat das problem nicht.
- nach reload wird ein dot erst nach der intervall zeit hervorgehoben.
- der inhalt kann nicht gezogen werden (maus gedrückt halten und inhalt vom swiper nach rechts/links ziehen).
  dies ist mit und ohne nutzung der @click funktion der fall.

als demo wie der swiper in ftui2 funktioniert hat (und meiner meinung nach auch in ftui3 funktionieren sollte) kann hier getestet werden: swiper demo
die Autoplay version ist hier mein persönlicher favorit und spiegelt gut das ftui2 verhalten wieder.

Du darfst diesen Dateianhang nicht ansehen.
[bild: scrollbalken im ff]

p.s: sag bescheid wenn du unter druck schneller arbeiten kannst, nörgeln kann ich nämlich viel besser als coden ;D 
[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

mr_petz

Für keine scrollbar in FF, in der swiper.component.css bei der class slides das mit einfügen (nach Zeile 14):
  scrollbar-width: none;
setstate hat das aber glaube gewollt. Für Chrome hat er die scrollbar anpassbar gemacht...

LG

Jones

Zitat von: mr_petz am 24 Juli 2023, 09:00:35setstate hat das aber glaube gewollt.
nimms mir nicht übel, aber ich kann mir nicht vorstellen das unterschiedliches verhalten in ff/chrome gewünscht sein soll.

hatte das mit
overflow-x: hidden;ausgeschaltet.
trotzdem bleibt es ein widget, was extrem weit weg ist von einem swiper :'(
habe jetzt schonmal angefangen mit der component weatherwarning.js, dazu brauche ich aber einen funktionierenden swiper. aber urlaub ist eh vorbei, wird jetzt alles nur sehr langsam weitergehen.

ihr macht mich echt fertig... nicht nur js, css und son kram, nein jetzt muss ich auch noch inkscape lernen.
(hintergrund: tablet hat internetsperre, kann also nicht die icons vom server laden. muss jetzt entweder gute freie warnschilder finden oder selber machen)
[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

mr_petz

Nimm es mir nicht übel, aber FTUI3 ist noch nicht im finalen Zustand. Da fängt es mit Bugs an und hört mit der Doku auf.
Bsp. im Chartsektor ist noch viel zu tun...

ps. Das overflow-x: hidden; lässt aber nur den horizontalen Scrollbalken verschwinden. Wenn die Höhe nicht zum Inhalt passt, dann kommt immer noch der vertikale Balken hinzu...

LG

yersinia

Zitat von: Jones am 24 Juli 2023, 13:22:24ihr macht mich echt fertig... nicht nur js, css und son kram, nein jetzt muss ich auch noch inkscape lernen.
(hintergrund: tablet hat internetsperre, kann also nicht die icons vom server laden. muss jetzt entweder gute freie warnschilder finden oder selber machen)
...du kannst die svgs auch dynamisch bauen - oder es mit CSS machen wenn du die icons/fontset bekommst. Hab ich mal für die DWD Warnungen gemacht - nicht perfekt aber für mich reicht es.
viele Grüße, yersinia
----
FHEM 6.4 (SVN) on RPi 4B with RasPi OS Bookworm (perl 5.36.0) | FTUI
nanoCUL->2x868(1x ser2net)@tsculfw, 1x433@Sduino | MQTT2 | Tasmota | ESPEasy
VCCU->14xSEC-SCo, 7xCC-RT-DN, 5xLC-Bl1PBU-FM, 3xTC-IT-WM-W-EU, 1xPB-2-WM55, 1xLC-Sw1PBU-FM, 1xES-PMSw1-Pl

Jones

Zitat von: mr_petz am 24 Juli 2023, 13:32:38Nimm es mir nicht übel, aber FTUI3 ist noch nicht im finalen Zustand. Da fängt es mit Bugs an und hört mit der Doku auf.
Bsp. im Chartsektor ist noch viel zu tun...
hehe, ich wollte hier keinem auf die füße treten, aber trotzdem klarstellen das ein unterschiedliches verhalten nicht gewünscht sein kann.
gerade weil es nicht final ist traue ich mich hier mit meinen, erst im anfang befindlichen kenntnissen, mitzumachen.

Zitat von: mr_petz am 24 Juli 2023, 13:32:38ps. Das overflow-x: hidden; lässt aber nur den horizontalen Scrollbalken verschwinden. Wenn die Höhe nicht zum Inhalt passt, dann kommt immer noch der vertikale Balken hinzu...
ok, das mit der höhe kam bei mir noch nicht vor, deine version ist dann definitive besser.

Zitat von: yersinia am 24 Juli 2023, 13:34:05...du kannst die svgs auch dynamisch bauen - oder es mit CSS machen wenn du die icons/fontset bekommst. Hab ich mal für die DWD Warnungen gemacht
sher schön, das werde ich mir mal anschauen...
[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

Jones

Zitat von: yersinia am 24 Juli 2023, 13:34:05...du kannst die svgs auch dynamisch bauen - oder es mit CSS machen wenn du die icons/fontset bekommst. Hab ich mal für die DWD Warnungen gemacht - nicht perfekt aber für mich reicht es.
habe mir die arbeit von dir mal angeguckt und direkt 2 fragen:
  • warum hast du noch icons benutzt? wäre doch besser wenn das warndreieck und der inhalt (blitz, schnee, etc) aus dem css kommen.
  • warum liegen die files im root verzeichnis und nicht in einer component?
eigentlich braucht es dann ja keine wetterwarnung component von mir.
wir können ja einen deal machen:
du baust als 2. device uwz bei dir ein und ich baue als 2. device dwd in mein weatherdetail ein.
(aber urlaub ist ende, wird mehr als 1,2 tage dauern bei mir)
[FTUI3] Addons: https://github.com/mr-petz/ftui/tree/addons
Manchmal habe ich Angst, dass ich euch nerve, aber dann fällt mir ein: Ihr seid ja freiwillig hier!

yersinia

[OT]
Zitat von: Jones am 26 Juli 2023, 14:58:22warum hast du noch icons benutzt? wäre doch besser wenn das warndreieck und der inhalt (blitz, schnee, etc) aus dem css kommen.
(1) aus der Historie heraus ('hamwa immer schon so gemacht' bzw sollte es eigtl erstmal nur das FTUI2 Modul ablösen)
(2) die icons waren da und sind leicht zu bekommen - und leicht einzubinden (siehe auch die FTUI3 Historie dazu)
(3) dies über je event_id als eigene CSS Klassen zu realisieren kam mir nicht in den Sinn 'damals' - könnte man lösen und dann die zusätzliche JS-Datei weglassen. Dennoch müssten die svgs via background-image oä. in das HTML-Objekt geladen werden. Man könnte den benötigten svg Code direkt übernehmen - könnte aber ein copyright/left Problem generieren. Die derzeitige Version halte ich für vertretbar pflegbar.

Zitat von: Jones am 26 Juli 2023, 14:58:22warum liegen die files im root verzeichnis und nicht in einer component?
Durch gegebene Standardfunktionalität, welche FTUI3 bereits bietet, bedarf es imho keiner eigenen component. Was soll eine component besser machen als die derzeitige Lösung? Mal vom Aufwand abgesehen, dies in die eigene Installation zu implementieren (vs zB dem addon repo). Es ist ja nur eine Event-basierte Anzeige von Readings. Die einzig 'höhere' Logik, wenn man dies überhaupt so nennen darf, ist das mapping der event_id auf eine wi-svg.
Spannend wäre allerdings, ob eine component wesentlich ressourcenschonender und schneller als die derzeitige Lösung sein würde.

Zitat von: Jones am 26 Juli 2023, 14:58:22eigentlich braucht es dann ja keine wetterwarnung component von mir.
Das UWZ Modul generiert etwas andere Warnings/Readings als das DWD Modul - es gibt hier durchaus Doubletten (so zumindest meine Erfahrung). Eine Component könnte geschickt Doubletten ausblenden - was wiederum dem Konzept des FTUI3 als imho reine AnzeigeGUI widersprechen würde. Du könntest dir das FTUI2 UWZ Widget ansehen.

Zitat von: Jones am 26 Juli 2023, 14:58:22wir können ja einen deal machen:
du baust als 2. device uwz bei dir ein und ich baue als 2. device dwd in mein weatherdetail ein.
Danke, nein. ;)
Zumal es sich die Frage stellt, ob man Warnungen vom DWD/UWZ in der weatherdetail Ansicht haben möchte.
[/OT]
viele Grüße, yersinia
----
FHEM 6.4 (SVN) on RPi 4B with RasPi OS Bookworm (perl 5.36.0) | FTUI
nanoCUL->2x868(1x ser2net)@tsculfw, 1x433@Sduino | MQTT2 | Tasmota | ESPEasy
VCCU->14xSEC-SCo, 7xCC-RT-DN, 5xLC-Bl1PBU-FM, 3xTC-IT-WM-W-EU, 1xPB-2-WM55, 1xLC-Sw1PBU-FM, 1xES-PMSw1-Pl