Changeset - b0ea577c12a3
[Not reviewed]
default
0 3 0
drewp@bigasterisk.com - 8 years ago 2017-06-07 04:32:10
drewp@bigasterisk.com
WIP colorpick into timeline. working on initial-paint bugs
Ignore-this: 497c157da0ff57cc6f5a66eba254e30c
3 files changed with 16 insertions and 8 deletions:
0 comments (0 inline, 0 general)
light9/web/light9-color-picker.html
Show inline comments
 
<link rel="import" href="/lib/polymer/polymer.html">
 
<link rel="import" href="/lib/paper-slider/paper-slider.html">
 

	
 
<dom-module id="light9-color-picker">
 
  <template>
 
    <style>
 
     :host {
 
         position: relative;
 
         display: flex;
 
         align-items: center;
 
     }
 
     #smallRainbowComp, #largeRainbowComp {
 
         display: inline-block;
 
         overflow: hidden;
 
         position: relative;
 
     }
 
     #smallRainbow {
 
         background: url(/colorpick_rainbow_small.png);
 
         width: 150px; 
 
         height: 30px;
 
     }
 
     #largeRainbow {
 
         background: url(/colorpick_rainbow_large.png);
 
         width: 400px; 
 
         height: 200px;
 
     }
 
@@ -54,62 +55,63 @@
 
         top: -110px;
 
     }
 
    </style>
 
    <div id="smallRainbowComp">
 
      <div id="smallRainbow" on-mouseenter="onEnterSmall"></div>
 
      <div id="smallCrosshair"></div>
 
    </div>
 
    <span>V:</span>
 
    <paper-slider min="0"
 
                  max="255"
 
                  step="1"
 
                  value="{{sliderWriteValue}}"
 
                  immediate-value="{{value}}"></paper-slider>
 
    <div id="largeRainbowComp">
 
      <div id="largeRainbow"
 
           on-mousemove="onCanvasMove"
 
           on-mouseup="hideLarge"
 
           on-mouseleave="hideLarge"></div>
 
      <div id="largeCrosshair"></div>
 
    </div>
 
  </template>
 
  <script src="/lib/color/one-color.js"></script>
 
  <script>
 
   class RainbowCanvas {
 
       constructor(url, size) {
 
       constructor(url, size, onReady) {
 
           this.size = size;
 
           var elem = document.createElement('canvas');
 
           elem.width = size[0];
 
           elem.height = size[1];
 

	
 
           this.ctx = elem.getContext('2d');
 

	
 
           this.colorPos = {} // color: pos
 
           
 
           var img = new Image();
 
           img.onload = function() {
 
               this.ctx.drawImage(img, 0, 0);
 
               this._readImage();
 
               if (onReady) onReady();
 
           }.bind(this);
 
           img.src = url;
 
       }
 
       _readImage() {
 
           var data = this.ctx.getImageData(
 
               0, 0, this.size[0], this.size[1]).data;
 
           for (var y = 0; y < this.size[1]; y+=1) {
 
               for (var x = 0; x < this.size[0]; x+=1) {
 
                   var base = (y * this.size[0] + x) * 4;
 
                   var c = one.color([data[base + 0],
 
                                      data[base + 1],
 
                                      data[base + 2], 255]).hex();
 
                   this.colorPos[c] = [x, y];
 
               }
 
           }
 
       }       
 
       colorAt(pos) {
 
           var data = this.ctx.getImageData(pos[0], pos[1], 1, 1).data;
 
           return one.color([data[0], data[1], data[2], 255]).hex();
 
       }
 
       posFor(color) {
 
           if (color == '#000000') {
 
               throw new Error('no match');
 
           }
 
@@ -144,76 +146,83 @@
 
   }
 
   
 
   Polymer({
 
       is: "light9-color-picker",
 
       properties: {
 
           color: {
 
               type: String,
 
               notify: true,
 
           },
 
           hueSatColor: { type: String, notify: true, value: '#000000' },
 
           value: { type: Number, notify: true }, // 0..255
 
           sliderWriteValue: { type: Number, notify: true },
 
       },
 
       observers: [
 
           'readColor(color)',
 
           'onValue(value)',
 
           'writeColor(hueSatColor, value)'
 
       ],
 
       attached: function() {
 
           if (!window.pickerCanvases) {
 
               window.pickerCanvases = {
 
                   large: new RainbowCanvas(
 
                       '/colorpick_rainbow_large.png', [400, 200]),
 
                   small: new RainbowCanvas(
 
                       '/colorpick_rainbow_small.png', [150, 30]),
 
                       '/colorpick_rainbow_small.png', [150, 30],
 
                       function() {
 
                           // color may have been set before our image came
 
                           this.readColor(this.color);
 
                       }.bind(this)),
 
               };
 
           }
 
           this.large = window.pickerCanvases.large;
 
           this.small = window.pickerCanvases.small;
 
       },
 
       onValue: function(value) {
 
           let neverBlack = .1 + .9 * value / 255;
 
           this.$.smallRainbow.style.filter = `brightness(${neverBlack})`;
 
       },
 
       writeColor: function(hueSatColor, value) {
 
           this.color = one.color(hueSatColor).value(value / 255).hex();
 
       },
 
       readColor: function(color) {
 
           if (this.$.largeRainbowComp.style.display == 'block') {
 
               // for performance, don't do color searches on covered widget
 
               return;
 
           }
 
           
 
           console.log('pos', color)
 
           // setting immediate-value doesn't work
 
           this.sliderWriteValue = one.color(color).value() * 255;
 
           
 
           var colorValue = one.color(color).value() * 255;
 
           this.sliderWriteValue = colorValue;
 
           try {
 
               var pos = this.small.posFor(color);
 
           } catch(e) {
 
               console.log('err')
 
               this.moveSmallCrosshair([-999, -999]);
 
               return;
 
           }
 
           console.log('go', pos)
 
           this.moveSmallCrosshair(pos);
 
       },
 
       _floatLarge: function() {
 
           // Large might span multiple columns, and chrome won't
 
           // send events for those parts. Workaround: take it out of
 
           // the columns.
 
           let large = this.$.largeRainbowComp;
 
           let rect = this.$.smallRainbowComp.getBoundingClientRect();
 
           document.body.append(large);
 
           large.style.position = 'fixed';
 
           large.style.left = (rect.left) + 'px';
 
           large.style.top = (rect.top - 50) + 'px';
 
       },
 
       showLarge: function() {
 
           this._floatLarge();
 
           this.$.largeRainbowComp.style.display = 'block';
 
           try {
 
               this.moveLargeCrosshair(this.large.posFor(this.color));
 
           } catch(e) {
 
               this.moveLargeCrosshair([-999, -999]);
 
               return;
 
           }
 
       },
 
       hideLarge: function() {
light9/web/timeline/timeline-elements.html
Show inline comments
 
<link rel="import" href="/lib/polymer/polymer.html">
 
<link rel="import" href="/lib/iron-resizable-behavior/iron-resizable-behavior.html">
 
<link rel="import" href="/lib/iron-ajax/iron-ajax.html">
 
<link rel="import" href="light9-timeline-audio.html">
 
<link rel="import" href="../rdfdb-synced-graph.html">
 
<link rel="import" href="../light9-music.html">
 
<link rel="import" href="../light9-color-picker.html">
 
<link rel="import" href="../edit-choice.html">
 

	
 

	
 
<!-- Whole editor- include this on your page.
 
     Most coordinates are relative to this element.
 
   -->
 
<dom-module id="light9-timeline-editor">
 
  <template>
 
    <style>
 
     :host {
 
         background: #444;
 
         display: flex;
 
         flex-direction: column;
 
         position: relative;
 
         border: 1px solid black;
 
         overflow: hidden;
 
     }
 
     light9-timeline-audio {
 
         width: 100%;
 
         height: 30px;
 
     }
 
     light9-timeline-time-zoomed {
 
         flex-grow: 1;
 
     }
 
@@ -312,47 +313,45 @@ background: rgba(126, 52, 245, 0.0784313
 
    </div>
 
    
 
  </template>
 
</dom-module>
 

	
 
<!-- sometimes we draw attrs within the shape of a note. -->
 
<dom-module id="light9-timeline-note-inline-attrs">
 
  <template>
 
    <style>
 
     #top {
 
         position: absolute;
 
         overflow: hidden;
 
         background: rgba(123, 123, 123, 0.71);
 
         border-radius: 6px;
 
         border: 1px solid #313131;
 
         padding: 3px;
 
         z-index: 2;
 
     }
 
    </style>
 
    <div id="top" style$="left: [[rect.left]]px; top: [[rect.top]]px; width: [[rect.width]]px; height: [[rect.height]]px; display: [[rect.display]]">
 
      <div>note [[noteLabel]] <button on-click="onDel">del</button></div>
 
      <table>
 
        <tr><th>effect:</th><td><edit-choice uri="{{effect}}" label="{{effectLabel}}"></edit-choice></td></tr>
 
        <tr><th>colorScale:</th><td>
 
          <!-- this could share with live/index.html's
 
          light9-live-control, but that one is currently junky -->
 
          <span><input type="color" value="{{colorScale::input}}"></span>
 
          <light9-color-picker color="{{colorScale}}"></light9-color-picker>
 
        </td></tr>
 
      </table>
 
    </div>
 
  </template>
 
</dom-module>
 

	
 
<script src="/lib/sylvester/sylvester.js"></script>
 
<script src="/lib/d3/build/d3.min.js"></script>
 

	
 
<!-- version with https://github.com/RubenVerborgh/N3.js/pull/61 -->
 
<script src="/lib/N3.js-pull61/browser/n3-browser.js"></script>
 
<!-- master version -->
 
<xxscript src="/lib/N3.js/browser/n3-browser.js"></script>
 
  
 
<script src="/lib/knockout/dist/knockout.debug.js"></script>
 
<script src="/lib/shortcut/index.js"></script>
 
<script src="/lib/async/dist/async.js"></script>
 
<script src="/lib/underscore/underscore-min.js"></script>
 
<script src="adjustable.js"></script>
 
<script src="timeline.js"></script>
light9/web/timeline/timeline.coffee
Show inline comments
 
@@ -481,49 +481,49 @@ Polymer
 
    yForV = (v) => @offsetTop + (1 - v) * @offsetHeight
 

	
 
    originTime = @graph.floatValue(@uri, U(':originTime'))
 
    effect = @graph.uriValue(@uri, U(':effectClass'))
 
    for curve in @graph.objects(@uri, U(':curve'))
 
      if @graph.uriValue(curve, U(':attr')) == U(':strength')
 
        @updateStrengthCurveEtc(originTime, curve, yForV, effect)
 
        
 
  updateStrengthCurveEtc: (originTime, curve, yForV, effect) ->
 
    U = (x) => @graph.Uri(x)
 
    [@pointUris, @worldPts] = getCurvePoints(@graph, curve, originTime) # (song time, value)
 

	
 
    curveWidth = =>
 
      tMin = @graph.floatValue(@worldPts[0].uri, U(':time'))
 
      tMax = @graph.floatValue(@worldPts[3].uri, U(':time'))
 
      tMax - tMin            
 

	
 
    screenPts = ($V([@zoomInX(pt.e(1)), @offsetTop + (1 - pt.e(2)) * @offsetHeight]) for pt in @worldPts)
 
    @dia.setNote(@uri, screenPts, effect)
 

	
 
    leftX = Math.max(2, screenPts[Math.min(1, screenPts.length - 1)].e(1) + 5)
 
    rightX = screenPts[Math.min(2, screenPts.length - 1)].e(1) - 5
 
    if screenPts.length < 3
 
      rightX = leftX + 120
 
    w = 150
 
    w = 430
 
    h = 80
 
    @inlineRect = {
 
      left: leftX,
 
      top: @offsetTop + @offsetHeight - h - 5,
 
      width: w,
 
      height: h,
 
      display: if rightX - leftX > w then 'block' else 'none'
 
      }
 

	
 
    if screenPts[screenPts.length - 1].e(1) - screenPts[0].e(1) < 100
 
      @clearAdjusters()
 
      # also kill their connectors
 
      return
 

	
 
    @makeCurveAdjusters(curveWidth, yForV, @worldPts)
 
    
 
  makeCurveAdjusters: (curveWidth, yForV, worldPts) ->
 
    U = (x) => @graph.Uri(x)
 

	
 
    if true
 
      @adjusterIds[@uri+'/offset'] = true
 
      @setAdjuster(@uri+'/offset', => new AdjustableFloatObject({
 
        graph: @graph
 
        subj: @uri
0 comments (0 inline, 0 general)