<input type="mathematik">
dedlfix
- javascript
- mathematik
Tach!
Gegeben sei ein Input-Element vom Typ range
, also ein Slider. Der soll sich so verhalten, dass in der Mitte der Wert 1 liegt, Maximalwert soll 100 sein und Minimalwert 0.01. Aber so einfach ist es ja nicht. So ein Range-Input arbeitet linear, und ich brauch da wohl was logarithmisches oder vielleicht auch was anderes. Das ganze soll einen Multiplikator darstellen. Auf der rechten Seite oberhalb von 1 soll es im unteren Bereich recht fein verstellbar sein, und je weiter man zum Maximalwert kommt, desto weniger interessiert es, ob man da genaue Werte trifft. Analog dazu sollte es auf der linken Seite unterhalb von 1 zugehen. Wobei ich mir da noch nicht ganz sicher bin, da müsste ich mal sehen, wie es sich dann letztlich anfühlt, also welche Bewegung welche Änderung ergibt.
Aber wie gesagt, sowas kann der Range-Input nicht und man wird da was rechnen müssen, um von einem linearen Messwertgeber auf das gewünschte Verhalten zu kommen. Nur was? Meine Mathekenntnisse sind jedenfalls eingerostet.
Ich hab da auch mal ein kleines Fiddle vorbereitet. Falls es kaputtgeht, das ist der wesentliche Teil:
<input type="range" id="in" min="0" max="10000" step="1">
<output id="out"></output>
var inElement = document.querySelector('#in');
var outElement = document.querySelector('#out');
outElement.value = inElement.value;
inElement.addEventListener('input', function(event) {
outElement.value = f(inElement.value);
});
function f(x) {
return x;
}
Die Funktion f() wäre also der gefragte Teil, wobei es mir hier auf die Idee ankommt, wie es zu lösen geht, und nicht auf den konkreten Code dazu. Die Werte von min, max und step sind keine Vorgaben und können am Ende so sein, wie es am besten für die Lösung passt.
dedlfix.
Du willst wahrscheinlich sowas:
ValueErrechnet = 10^(V/2)-1
Der Input liefert 0 bis 9.
V : ValueErrechnet
--------------------
0 : 0
1 : 2,16227766016838
2 : 9
3 : 30,6227766016838
4 : 99
5 : 315,227766016838
6 : 999
7 : 3161,27766016838
9 : 31621,7766016838
Spiele in der Formel mit der 10 und der 2 für Deine konkrete Anwendung...
Andere Lösung, mit Sprüngen an den Grenzen der 10er-Potenzen:
for( i = 1; i < 7; i++ ) {
if ( V < 10 ^ i + 1 ) {
return V * 10 ^ ( i - 1 );
}
}
Du kannst statt der 10er Potenzen auch 2 oder sonstwas nehmen.
Tach!
Du willst wahrscheinlich sowas:
ValueErrechnet = 10^(V/2)-1
Vermutlich, aber in der konkreten Form ist das für mich nicht das gewünschte. Hier muss ich erstmal die Formel umstellen, um die für die gewünschten Grenzen die passenden Parameter zu errechnen, damit der Slider richtig kalibriert ist. Und dann sitzt die 1 leider auch noch nicht in der Mitte.
Die Idee geht in die richtige Richtung, die 10^X-Variante ist da aber einfacher zu handhaben und skaliert in beide Richtungen gleich gut. Um den am Slider einzustellenden Grenzwert zu bekommen, geht die vergleichbar einfache Formel: Logarithmus zur Basis 10 vom Grenzwert des eigentlich gewünschten Bereichs.
Aber vielleicht hat deine Lösung noch andere Vorteile, die ich aber aufgrund meines eingestaubten Wissens (und ebensolchem Tafelwerk) nicht erkenne.
dedlfix.
@@dedlfix
Um den am Slider einzustellenden Grenzwert zu bekommen, geht die vergleichbar einfache Formel: Logarithmus zur Basis 10 vom Grenzwert des eigentlich gewünschten Bereichs.
Wenn du nicht die im Dezimalsystem runden Grenzen 0.01 und 100 haben willst, kannst du den natürlichen Logarithmus nehmen und statt Math.pow(10, x)
dann Math.exp(x)
– und der Rechner hat weniger zu tun. #mikrooptimierung
LLAP 🖖
Man kann beides haben:
Da stets gilt $$a^x=e^{x \cdot ln a}$$ (was man durch beidseitiges Anwenden der $$ln$$-Funktion bestätigt), hat man insbesondere
$$10^x=e^{x \cdot ln 10}=exp(2.3026 \cdot x)$$
Der Rechner tut sich leichter, und man bekommt trotzdem die Grenzen 0.01 und 100 heraus.
Hallo,
zumindest für Intel x86/x64 gilt: Ob Exp oder 10^x - das muss mit $$x^y=2^{ylog2(x)}$$ approximiert werden. Es gibt eine Instruktion für $$ylog2(x)$$ und eine Instruktion für $$2^{x-1}$$, mit Einschränkungen auf dem Wertebereich, so dass man mit den Exponenten der Fließkommawerte herumfiddeln muss bevor man im erlaubten Bereich ist. Und das ist dem Vernehmen nach auch noch ungenau, man muss das noch nachbehandeln. Ich kann nicht sagen, dass ich José da wirklich verstanden hätte.
D.h. man muss exp und 10^x beide auf 2^x abbilden, weshalb es wurscht ist, ob man Math.pow oder Math.exp verwendet.
Wie es auf anderen Prozessoren aussieht, weiß ich nicht.
Rolf
@@dedlfix
Gegeben sei ein Input-Element vom Typ
range
, also ein Slider. Der soll sich so verhalten, dass in der Mitte der Wert 1 liegt
1 = 10⁰
Maximalwert soll 100 sein
100 = 10²
und Minimalwert 0.01.
0.01 = 10⁻²
Aber so einfach ist es ja nicht. So ein Range-Input arbeitet linear
wie z.B. von −2 bis 2, wobei 0 in der Mitte ist.
Wenn du den Wert des Sliders als Exponent zur Basis 10 nimmst, deckst du den gewünschten Bereich von 0.01 bis 100 ab, mit 1 in der Mitte.
☞ Codepen
LLAP 🖖
Tach!
Aber so einfach ist es ja nicht. So ein Range-Input arbeitet linear
wie z.B. von −2 bis 2, wobei 0 in der Mitte ist.
Wenn du den Wert des Sliders als Exponent zur Basis 10 nimmst, deckst du den gewünschten Bereich von 0.01 bis 100 ab, mit 1 in der Mitte.
Ja, sehr schön. So hab ich mir das vorgestellt.
Als ich mir die Kurve dazu hab malen lassen, hab ich mir gedacht: Das steigt zwar schön auf der rechten Seite an, aber was ist mit der linken? Aber das muss ja so sein. In einem linearen System ist zwischen 0 und 1 eben weniger Platz als zwischen 1 und 100. Ich war fälschlicherweise auf der Suche nach einer Kurve, die beidseitig vergleichbar aussieht. So eine bekommt man (vermute ich mal) zwar hin, aber es ist dann eine Gerade in einem System mit einer logarithmischen(?) Achse. Als Gerade sieht sie dann unspektakulär aus, aber ist eigentlich genau das was ich haben wollte.
☞ Codepen
Kritik am Antwortgeber ist zwar im Allgemeinen nicht gern gesehen, ich übe sie mal trotzdem, weil ich weiß, dass du das nicht falsch verstehst. Deine Vorliebe für den Codepen in Ehren, aber dass ich als Spielwiese JSFiddle ausgesucht habe, hatte schon seinen Grund. Der ist, dass der Codpen übermäßig viel Platz (~50%) für die Ausgabe verwendet, in dem Fall aber die Ausgabe nur sehr klein ist. Das geht zu Lasten der Code-Teile, die im restlichen Teil sehr gequetscht aussehen. Die etwas höhere Schriftgröße trägt ebenfalls ihr Schärflein dazu bei. Resultat ist, dass so gut wie jede Codezeile umgebrochen werden muss, wenn man nicht gerade ein Sauna-Handtuch quergelegt als Bildschirmgröße hat. Das macht das Lesen recht mühsam. Ja, man kann die Code-Bereiche größenverändern, aber das geht immer zu Lasten der anderen beiden. Die Aufteilung beim JSFiddle empfinde ich in dem Fall deutlich komfortabler und als das für die Situation besser geeignete Werkzeug. Im Mittelpunkt stand ja auch das Javascript und weniger die HTML-Ausgabe.
dedlfix.
Hallo dedlfix,
jsFiddle ist ja ab Werk auf "gerechter Anteil für alle" eingestellt und du kannst das hin- und herschieben.
Das geht in Codepen auch, und die relative Anordnung kannst Du über ChangeView verändern. Man bekommt damit ein ziemlich großes JS-Fenster hin.
Bei der Gelegenheit wollte ich übrigens "Full Screen" in CodePen ausprobieren, und, tja, was soll ich da jetzt sagen. Auf CodePen steht: "Feel free to pinch them in the leg for us."
Sorry Gunnar, das tut jetzt ein bisschen weh… KNEIF 😉
Rolf
Tach!
Das geht in Codepen auch, und die relative Anordnung kannst Du über ChangeView verändern. Man bekommt damit ein ziemlich großes JS-Fenster hin.
Im Change View finde ich nur die normale Editor View als das kleinere Übel. Alle anderen Ansichten gehen entweder nicht oder zeigen keinen Code. ... Ach, da unten in dem Menü gibts noch Editor Layout. Ja, das passt schon besser, wenn die Code-Teile links untereinander stehen und die Ausgabe rechts. Da kann man sich das angenehmer zurechtschieben. Kann man das als Ersteller so voreinstellen, dass man eine zum Problem besser passende Darstellung definieren kann, oder geht das nur individuell, wenn man weiß, wo man hingreifen muss?
Jedenfalls löst sich damit ein Großteil der Kritik auf und Codepen lässt sich doch auf ein für diesen Fall passendes Werkzeug einstellen.
dedlfix.