Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Select box open onclick direction -- display data both upwards and downwards

Not too sure if this question qualifies for SO, perhaps borderline. If it doesnt kindly inform me and I'll modify accordingly.

Ive searched every corner of the intraweb for a library or tutorial for the following, but simply cant find one.

Im trying to display a select box, which onclick moves half the options upwards and half the options downwards as in the image below:

enter image description here

Ive seen a javascript library where instead of the default option where the data in a select box gets displayed downwards -- it gets display upwards.

However I cant find anything to achieve the effect on above where half the data essentially gets displayed in an upwards direction and other half in a downward direction.

If anyone can provide some input it would be immensely appreciated.

like image 284
gekkogurru Avatar asked Jan 13 '18 14:01

gekkogurru


People also ask

Does onClick work on select?

Neither the onSelect() nor onClick() events are supported by the <option> tag. The former refers to selecting text (i.e. by clicking + dragging across a text field) so can only be used with the <text> and <textarea> tags.

How do I style a selection dropdown in CSS?

There are many ways to design a <select> dropdown menu using CSS. The Dropdown Menu is mainly used to select an element from the list of elements. Each menu option can be defined by an <option> element that can nested inside the <select> element.

How can I show a hidden div when a select option is selected?

To show a hidden div when a select option is selected, you can set the value “style. display” to block.

How do you hide a drop-down list in HTML?

We use <select> and <option> elements to create a drop-down list and use disabled attribute in <select> element to disable the drop-down list element.


2 Answers

If a jump-appear solution (instead of animation) is an option, you can get away with pure CSS an no javascript at all.

HTML select direction can't be controlled as it's up to each browser, but you could use instead radio buttons and control related labels. Then it's just a matter of controlling the display of the labels on hover.

html{
  font-family:sans-serif;
  box-sizing:border-box;
}

input{
  display:none;
}
label{
  display:none;
  padding:1em;
  width: 300px;
}

input:checked + label{
  background:green;
  display:block;
}

#container{
  border:1px solid lightblue;
  position:absolute;
  top:50%; left:50%;
  transform:translate(-50%);
}

#container:hover{
  transform:translate(-50%, calc(-50% + 2em));
}

#container:hover label{
  cursor: pointer;
  display:block;
  border-bottom:1px solid lightblue;
}
<div id="container">
  <input type="radio" name="result" id="f2">
  <label for="f2"> France 2</label>
  <input type="radio" name="result" id="f1">
  <label for="f1"> France 1</label>
  <input type="radio" name="result" id="0" checked>
  <label for="0"> Draw</label>
  <input type="radio" name="result" id="i1">
  <label for="i1"> Ireland 1</label>
    <input type="radio" name="result" id="i2">
  <label for="i2"> Ireland 2</label>
</div>

Edit:

Apparently in my frenzy of "you can do that with pure CSS" I forgot it's 2018, and the above answer will only work for desktop and fail miserably on mobile, as it relies on :hover. So we need a little JS, just to toggle an ".active" class instead of the hovers.

var container = document.getElementById("container");
var labels = document.querySelectorAll("#container label")
for (i = 0; i < labels.length; i++) {
  (function(i) {
    labels[i].addEventListener('click', function() {
      container.classList.toggle("active");
    });
  })(i);
}
html{
  font-family:sans-serif;
  box-sizing:border-box;
}

input{
  display:none;
}
label{
  display:none;
  padding:1em;
  width: 300px;
}

input:checked + label{
  display:block;
  background-color:green;
  color:white;
}

#container{
  border:1px solid lightblue;
  position:absolute;
  top:50%; left:50%;
  transform:translate(-50%);
}

#container.active{
  transform:translate(-50%, calc(-50% + 2em));
}

#container.active label{
  display:block;
  border-bottom:1px solid lightblue;
}

#container label{
  cursor: pointer;
}
<div id="container">
  <input type="radio" name="result" id="f2">
  <label for="f2"> France 2</label>
  <input type="radio" name="result" id="f1">
  <label for="f1"> France 1</label>
  <input type="radio" name="result" id="0" checked>
  <label for="0"> Draw</label>
  <input type="radio" name="result" id="i1">
  <label for="i1"> Ireland 1</label>
    <input type="radio" name="result" id="i2">
  <label for="i2"> Ireland 2</label>
</div>

Got some issues there trying to apply the click event to the container instead of each individual label, so that JS can surely be improved... any help will be appreciated.

Alternatively, you can just use jQuery for that. Talkin 'bout "I forgot it's 2018"...

$('#container label').click(function() {
  $(this).parent().toggleClass('active')
});
like image 78
Facundo Corradini Avatar answered Oct 03 '22 07:10

Facundo Corradini


Unless you can find a library which has this functionality built-in, you could resort to just manually change the position of the dropdown from pretty much any select library.

Here's a "simple" example using select2:

var disableSelection = false, selectionDisabledTimer;
$('#example').select2({ //#example is a select element
    minimumResultsForSearch: -1 //disable search
}).on('select2:open', function(){
    setTimeout(function(){
          var goUpBy = $('.select2-dropdown').height() / 2; //nr of px to move up
          $('.select2-dropdown')
            .removeClass('select2-dropdown--below') //remove style which hides upper border
            .css('marginTop', -goUpBy +'px');       //move dropdown up
    }, 0);
}).on('select2:opening', function(e){
    disableSelection = true;
    clearTimeout(selectionDisabledTimer);           //clear old timer (in case of multiple fast clicks)
    selectionDisabledTimer = setTimeout(function(){ //disable selection for 500ms
        disableSelection = false;
    }, 500);
}).on('select2:selecting', function(e){
    if(disableSelection){
        e.preventDefault();
    }
});

Demo: https://jsfiddle.net/981usa95/7/

Note: The code looks messy because I had to work around the issue where, because the dropdown is opened below the cursor, the option below the cursor is instantly selected. Cleaner solutions may exist.

like image 45
Alexandru Severin Avatar answered Oct 03 '22 09:10

Alexandru Severin