Learn how to toggle the visibility of three div elements arranged horizontally

$(document).ready(function () {
    $("#toggle").click(function () {
        if ($(this).data('name') == 'show') {
            $("#sidebar").animate({
                width: '10%'
            }).hide()
            $("#map").animate({
                width: '89%'
            });
            $(this).data('name', 'hide')
        } else {
            $("#sidebar").animate({
                width: '29%'
            }).show()
            $("#map").animate({
                width: '70%'
            });
            $(this).data('name', 'show')
        }
    });
});
html, body {
    width:100%;
    height: 100%;
}
#header {
    width: 100%;
    height: 20%;
    float: left;
    border: 1px solid;
}
#map {
    width: 80%;
    height: 80%;
    float: left;
    border: 1px solid;
}
#sidebar {
    width: 19%;
    height: 80%;
    float: left;
    border: 1px solid;
}
#toggle {
    width: 10%;
    height: 40%;
    margin-right: 6.5%;
    margin-top: 3.5%;
    float: right;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="header">HEADER
    <input type="button" data-name="show" value="Toggle" id="toggle">
</div>
<div id="map">MAP</div>
<div id="sidebar">SIDEBAR</div>

I am just starting out with angularjs, jquery, and css. I'd like to arrange three divs with a toggle side by side. Can anyone provide guidance on how to achieve this in angularjs?

In the regular mode, it should look like the following:

https://i.stack.imgur.com/Ma3HG.jpg

This is how it would appear.

If I extend the center div, it should look like the following example:

https://i.stack.imgur.com/ej7V7.jpg

If I expand the last div, it should resemble this example:

https://i.stack.imgur.com/QbW8S.jpg

Thank you!

Answer №1

Give this a try! You can expand all the divs in any order and switch them back to their normal position by clicking on the expanded div again.

The width of the compressed and expanded states are represented in percentages and can be adjusted in the CSS to fit your needs. I've also included a transition property for smoother functionality.

Check out the code snippet on this codepen link.

$("a.expansion-btn").click(function () {
  classes = this.className;
  var divNumber = classes.slice(-1);
  var toGetId = "#div-" + divNumber;
  if ($(toGetId).hasClass("expanded-div")) {
    $(".normal-div").removeClass("compressed-div expanded-div");
  } else {
    $(".normal-div").removeClass("compressed-div expanded-div").addClass("compressed-div");
    ;
    $(toGetId).removeClass("compressed-div").addClass("expanded-div");
  }
});
*{
  box-sizing: border-box;
}
.container{
  margin: 0;
  padding: 0;
  width: 100%;
  height: 400px;
}
.normal-div{
  width: 33.33%;
  height: 100%;
  position: relative;
  border: 2px solid black;
  float: left;
  -webkit-transition: all 0.5s ease-in-out;
  -moz-transition: all 0.5s ease-in-out;
  transition: all 0.5s ease-in-out;
}
.expanded-div{
  width: 80%;
}
.compressed-div{
  width: 10%;
}
#div-1{
  background-color: green;
}
#div-2{
  background-color: red;
}
#div-3{
  background-color: blue;
}
a.expansion-btn{
  position: absolute;
  top: 10px;
  right: 10px;
  font-weight: bold;
  cursor: pointer;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="container">
  <div class="normal-div" id="div-1">
    <a class="expansion-btn exp-1">click</a>
  </div>
  <div class="normal-div" id="div-2">
    <a class="expansion-btn exp-2">click</a>
  </div>
  <div class="normal-div" id="div-3">
    <a class="expansion-btn exp-3">click</a>
  </div>
</div>

Answer №2

If you're looking to switch between different divs, you can use the following code snippet.

// define variable to track div index
var i = 0,
  // cache all div elements
  $div = $('.div');

// attach click event handler
$('.toggle').click(function() {
  $div
    // remove active and nonactive classes from all elements
    .removeClass('active nonactive')
    // select element by index
    .eq(i)
    // add active class
    .addClass('active')
    // select siblings
    .siblings()
    // add nonactive class
    .addClass('nonactive');
  // update index 
  i = ++i % $div.length;
})
.div {
  height: 300px;
  width: 30%;
  border: solid 1px black;
  display: inline-block
}
.active {
  width: 75%;
}
.nonactive {
  width: 10%;
}
.active,
.nonactive {
  -webkit-transition: width 1s ease-in-out;
  -moz-transition: width 1s ease-in-out;
  -o-transition: width 1s ease-in-out;
  transition: width 1s ease-in-out;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button class="toggle">toggle</button>
<br>
<div class="div"></div>
<div class="div"></div>
<div class="div"></div>


Alternatively, if you prefer to toggle when clicking a button inside the div, consider this approach.

$('.toggle').click(function() {
  $(this)
    // find parent div
    .parent()
    // remove nonactive class from clicked element
    .removeClass('nonactive')
    // toggle active class
    .toggleClass('active')
    // get sibling divs
    .siblings()
    // remove active class from siblings
    .removeClass('active')
    // toggle nonactive class based on the clicked element 
    .toggleClass('nonactive', $(this).parent().is('.active'));
})
.div {
  height: 300px;
  width: 30%;
  border: solid 1px black;
  display: inline-block
}
.active {
  width: 75%;
}
.nonactive {
  width: 10%;
}
.div,
.active,
.nonactive {
  -webkit-transition: width 1s ease-in-out;
  -moz-transition: width 1s ease-in-out;
  -o-transition: width 1s ease-in-out;
  transition: width 1s ease-in-out;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
  <div class="div">
    <button class="toggle">toggle</button>
  </div>
  <div class="div">
    <button class="toggle">toggle</button>
  </div>
  <div class="div">
    <button class="toggle">toggle</button>
  </div>
</div>

Answer №3

    <div id="header">HEADER
        <input type="button" data-name="show" value="Toggle" id="toggle">
    </div>
    <div id="maincont">
        <div id="map" class="active">MAP</div>
        <div id="sidebar" class="inactive">SIDEBAR</div>
        <div id="sidebar1" class="inactive">SIDEBAR1</div>
    </div>

script:

    $(document).ready(function () {     
            $("#toggle").click(function () {

                        var $div = $('#maincont').find(".active");
                        $div.removeClass('active').addClass("inactive").next().addClass("active");      

                        $('#maincont').find(".inactive").animate({
                            width: '10%'
                        })

                        $('#maincont').find(".active").animate({
                            width: '79%'
                        });           

             });

    });

css.

         html, body {
            width:100%;
            height: 100%;
        }
        #header {
            width: 100%;
            height: 100px;
            float: left;
            border: 1px solid;
        }
        #map {  
            height: 80%;
            float: left;
            border: 1px solid;
        }
        .active{
          width:78%;
           float: left;
           height: 100px;
        }
        .inactive{
          width:10%;
           float: left;
           border: 1px solid;
            height: 100px;
        }
        #sidebar {   
            height: 80%;
            float: left;

        }
        #toggle {
            width: 10%;
            height: 40%;
            margin-right: 6.5%;
            margin-top: 3.5%;
            float: right;
        }

Link to the fiddle

Answer №4

Including the angularjs tag in your question led me to provide a straightforward solution without any complex CSS:

Assume you have an array of objects in the controller that define the panels/divs like this:

$scope.panels = [{
    title: "One",
    expanded: true
  }, {
    title: "Two"
  }, {
    title: "Three"
  }];

The expanded flag keeps track of which panel is currently expanded, defaulting to the first one.

When you click on a panel, this function updates the flag for the selected panel:

$scope.expandPanel = function(panel) {
     $scope.panels.forEach(p => p.expanded = false);
     panel.expanded = true;
}

To display this, use an ng-repeat loop and dynamically set the class based on the expanded flag using ng-class:

<div class="panel" 
     ng-class="{'expanded': panel.expanded, 'reduced': !panel.expanded}" 
     ng-repeat="panel in panels" ng-click="expandPanel(panel)">
  <span>{{panel.title}}</span>
</div> 

You can view this implementation live on this plunker link.

Note: The classes .panel, .expanded, and .reduced are defined in the plunker's CSS file.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

How to remove an extra horizontal scroll bar from a fixed-header HTML table?

While working on updating my HTML tables to have fixed headers, I followed online examples that suggest making table-layout fixed, thead and tbody blocks, setting height constraints for tbody, and applying overflow-y to tbody. The result is functional as m ...

Assign a CSS class to a specific option within a SelectField in a WTForms form

Could someone explain the process of assigning a CSS class to the choices values? I am looking to customize the background of each choice with a small image. How can this be done using wtforms and CSS? class RegisterForm(Form): username = TextField( ...

Error encountered when importing a Material-UI component: Unable to load a module from @babel/runtime

Struggling to compile the index.js file with rollup: import React from "react"; import ReactDOM from "react-dom"; import Grid from "@material-ui/core/Grid"; ReactDOM.render( <React.StrictMode> <Grid conta ...

ESLint error caught off guard by function expression in customized MUI Snackbar Component with Alert

Struggling to create a personalized MUI Snackbar using the MUI Alert example from the official Documentation, but facing ESlint errors: error Unexpected function expression prefer-arrow-callback error Prop spreading is forbidden react/jsx-props-no-s ...

Incorporating the click function into dynamically created divs using jQuery

When I receive an array from AJAX, I am dynamically creating Divs based on the number of items in the array. Each div has a unique Id and I want to attach a Click event to all of them. The goal is for the user to click on one of the generated divs to tri ...

Using JSON in combination with any client or server programming language allows for seamless

Is it possible to use any language as server and client sides if I choose JSON as the data exchange format? I am currently working on a web application using PHP and jQuery. My server delivers responses in JSON format, and now I want to develop an Android ...

Position elements in the center of the page at 33.3333% width

I'm facing a challenge with centering elements that are floated left and have a width of 33.33333% on the page. I want the text inside these elements to remain aligned to the left, but I'm unsure how to go about centering the items: ul.home-pr ...

Unraveling Vue Async Components - Harnessing the power of emitted events to resolve

I am looking to create a Vue async component that stays in a loading state until a custom event is triggered. This means it will render a specified loading component until the event occurs. Here's an example of how I want it to work: const AsyncComp ...

The JavaScript code that added links to the mobile menu on smaller screens is no longer functioning properly

I recently created a website with a mobile navigation menu that should appear when the browser width is less than 1024px. However, I used some JavaScript (with jQuery) to include links to close the menu, but now the site is not displaying these links and t ...

Receiving the most recent data in a protractor examination as a text string

My goal is to fetch an input value for a specific operation in protractor. I am attempting to make an ajax request using protractor and need to assign a unique value (referred to as groupCode) to a JSON object that will be sent to the server. Initially, I ...

Organize routes into distinct modules in Angular 6

Currently grappling with routing in my Angular 6 application. Wondering if the structure I have in mind is feasible. Here's what it looks like: The App module contains the main routing with a parent route defining the layout: const routes: Routes = ...

Incorporate axios within getStaticProps while utilizing Next.js

I am working on a new project where I am utilizing axios to handle request data. However, I am facing an issue when using axios in the getStaticProps function which results in an error on my index.js page. Here is a snippet of my index.js code: import ...

Issue with scroll being caused by the formatting of the jQuery Knob plugin

I am currently utilizing the jQuery Knob plugin and I am looking to have the displayed value shown in pound sterling format. My goal is for it to appear as £123456. However, when I attempt to add the £ sign using the 'format' hook, it causes is ...

Unifying flex and position:fixed

I'm having difficulties when it comes to displaying a modal dialog with a fixed position within a flex layout. The header and footer of the dialog need to be set in height, while the content section should have overflow with scrollbars. I chose the fl ...

Calendars malfunctioning following the execution of npm run build

While utilizing the vue2-datepicker for a calendar, I encountered an issue during development. When clicking on the input box in my form, the calendar appeared as expected above the input. However, after running npm run build and loading up the resulting p ...

Leveraging classes in routing with express framework

After deciding to convert the code from functions to classes, I ran into an issue where 'this' was undefined. Routing // router.js const ExampleController = require('./ExampleController'); const instanceOfExampleController = new Exam ...

Tips on containing the reach of a function in JavaScript/jQuery

I have a scenario where I have multiple .js files linked on the page, each containing functions with the same name. For example: first.js function DisplayContent(data,$target) // data is string { $target.html('<span>'+ data +'&l ...

Ensure that the sidebar automatically scrolls to the bottom once the main content has reached the bottom

I am facing an issue with a sticky sidebar that has a fixed height of calc(100vh-90px) and the main content. The sidebar contains dynamic content, which may exceed its defined height, resulting in a scrollbar. On the other hand, the main content is lengthy ...

What is the best way to accurately determine the height and offset values of an element while utilizing ng-repeat?

My objective is to determine the offset and height of list items. Once I have those values, I trigger a function in a parent directive. Ultimately, this will involve transitioning elements in and out as they come into view. Issue: Due to the use of ng-rep ...

How can I showcase both a username and email address in a Material UI chip?

I'm currently using Material UI chip to show name and email next to each other. However, when the name is long, the email goes beyond the chip boundary. Here's my function that generates the chips: getGuestList() { let {guests} = this.sta ...