Skip to content

Instantly share code, notes, and snippets.

@jrosesol
Forked from anonymous/index.html
Created May 2, 2016 14:19
Show Gist options
  • Save jrosesol/e60523e7ccdcfb46a878dda932ecfec1 to your computer and use it in GitHub Desktop.
Save jrosesol/e60523e7ccdcfb46a878dda932ecfec1 to your computer and use it in GitHub Desktop.
<!DOCTYPE html>
<meta charset="utf-8">
<style type="text/css">
.node {
cursor: pointer;
}
.overlay{
background-color:#EEE;
}
.node circle {
fill: #fff;
stroke: steelblue;
stroke-width: 1.5px;
}
.node text {
font-size:10px;
font-family:sans-serif;
}
.link {
fill: none;
stroke: #ccc;
stroke-width: 1.5px;
}
.templink {
fill: none;
stroke: red;
stroke-width: 3px;
}
.ghostCircle.show{
display:block;
}
.ghostCircle, .activeDrag .ghostCircle{
display: none;
}
</style>
<script src="https://code.jquery.com/jquery-1.10.2.min.js"></script>
<script src="https://d3js.org/d3.v3.min.js"></script>
<body>
<div id="tree-container"></div>
<script id="jsbin-javascript">
var treeData = {
"user_id": 0,
"name": "Root Node",
"children": [
{
"user_id": 0,
"name": "Flossie Hickman",
"children": [
{
"user_id": 0,
"name": "Violet Arnold",
"children": [
{
"user_id": 4,
"name": "Sabrina Harrell",
"children": [
{
"user_id": 0,
"name": "Dalton Norman"
},
{
"user_id": 1,
"name": "Barrett Morales"
},
{
"user_id": 2,
"name": "Daniels Booth"
},
{
"user_id": 3,
"name": "Maxwell Rich"
},
{
"user_id": 4,
"name": "Bennett Washington"
},
{
"user_id": 5,
"name": "Lelia Banks"
},
{
"user_id": 6,
"name": "Georgette Joyce"
},
{
"user_id": 7,
"name": "Kaitlin Irwin"
},
{
"user_id": 8,
"name": "Lacey Case"
},
{
"user_id": 9,
"name": "Reyes Jenkins"
},
{
"user_id": 10,
"name": "Rios Dunn"
},
{
"user_id": 11,
"name": "Walsh Robles"
},
{
"user_id": 12,
"name": "Nieves Ratliff"
},
{
"user_id": 13,
"name": "Alta Brennan"
},
{
"user_id": 14,
"name": "Theresa Gilliam"
}
]
},
{
"user_id": 13,
"name": "Cantu Griffin",
"children": [
{
"user_id": 0,
"name": "Gilmore Jordan"
},
{
"user_id": 1,
"name": "Mindy Mercado"
},
{
"user_id": 2,
"name": "Townsend Harmon"
},
{
"user_id": 3,
"name": "Bethany Mathis"
},
{
"user_id": 4,
"name": "Tonia Patel"
},
{
"user_id": 5,
"name": "Earnestine Foster"
},
{
"user_id": 6,
"name": "Wilson Evans"
},
{
"user_id": 7,
"name": "Olsen Wheeler"
},
{
"user_id": 8,
"name": "Mejia Hall"
},
{
"user_id": 9,
"name": "Viola Waller"
},
{
"user_id": 10,
"name": "Robbins Rivera"
},
{
"user_id": 11,
"name": "Lowe Yang"
},
{
"user_id": 12,
"name": "Riddle Cervantes"
},
{
"user_id": 13,
"name": "Rachel Soto"
},
{
"user_id": 14,
"name": "Gonzales Bond"
}
]
}
]
},
{
"user_id": 10,
"name": "Rosario Molina",
"children": [
{
"user_id": 0,
"name": "Robyn Garza",
"children": [
{
"user_id": 0,
"name": "Mable Hines"
},
{
"user_id": 1,
"name": "Angelica Mcdaniel"
},
{
"user_id": 2,
"name": "Raquel Cervantes"
},
{
"user_id": 3,
"name": "Nona Mcfadden"
},
{
"user_id": 4,
"name": "Pearl Mclaughlin"
},
{
"user_id": 5,
"name": "Bessie Ferguson"
},
{
"user_id": 6,
"name": "Gutierrez Collier"
},
{
"user_id": 7,
"name": "Rosanna Hopper"
},
{
"user_id": 8,
"name": "Eleanor Barlow"
},
{
"user_id": 9,
"name": "Krystal Wiley"
},
{
"user_id": 10,
"name": "Amalia Whitney"
},
{
"user_id": 11,
"name": "Hunt Dennis"
},
{
"user_id": 12,
"name": "Hobbs Doyle"
},
{
"user_id": 13,
"name": "Clarissa Bates"
},
{
"user_id": 14,
"name": "Ada Beck"
}
]
},
{
"user_id": 1,
"name": "Candace Gomez",
"children": [
{
"user_id": 0,
"name": "Bette Bolton"
},
{
"user_id": 1,
"name": "Mendoza Emerson"
},
{
"user_id": 2,
"name": "Natalie Powers"
},
{
"user_id": 3,
"name": "Bowen Massey"
},
{
"user_id": 4,
"name": "Lucia Hardy"
},
{
"user_id": 5,
"name": "Tillman Willis"
},
{
"user_id": 6,
"name": "Vinson Mcgowan"
},
{
"user_id": 7,
"name": "Leta Hoover"
},
{
"user_id": 8,
"name": "Barnett Gallegos"
},
{
"user_id": 9,
"name": "Keisha Bowen"
},
{
"user_id": 10,
"name": "Sharp Berger"
},
{
"user_id": 11,
"name": "Bates Davenport"
},
{
"user_id": 12,
"name": "Stuart Levy"
},
{
"user_id": 13,
"name": "Aurora Mercado"
},
{
"user_id": 14,
"name": "Callahan Sellers"
}
]
},
{
"user_id": 2,
"name": "Sharlene Mueller",
"children": [
{
"user_id": 0,
"name": "Selena Mooney"
},
{
"user_id": 1,
"name": "Iva Woodard"
},
{
"user_id": 2,
"name": "Olga Zimmerman"
},
{
"user_id": 3,
"name": "Christi Townsend"
},
{
"user_id": 4,
"name": "Augusta Rollins"
},
{
"user_id": 5,
"name": "Powell Bass"
},
{
"user_id": 6,
"name": "Morton Myers"
},
{
"user_id": 7,
"name": "Thompson Lowery"
},
{
"user_id": 8,
"name": "Sharon Soto"
},
{
"user_id": 9,
"name": "Maddox Potts"
},
{
"user_id": 10,
"name": "Heath Mayo"
},
{
"user_id": 11,
"name": "Oneal Bridges"
},
{
"user_id": 12,
"name": "Irene Conley"
},
{
"user_id": 13,
"name": "House Montoya"
},
{
"user_id": 14,
"name": "Jo Deleon"
}
]
},
{
"user_id": 3,
"name": "Erica Grimes",
"children": [
{
"user_id": 0,
"name": "Gloria Chapman"
},
{
"user_id": 1,
"name": "Vasquez Snyder"
},
{
"user_id": 2,
"name": "Ofelia Mclean"
},
{
"user_id": 3,
"name": "Jimenez Harvey"
},
{
"user_id": 4,
"name": "Jocelyn Joyner"
},
{
"user_id": 5,
"name": "Desiree Shaffer"
},
{
"user_id": 6,
"name": "Jana Delgado"
},
{
"user_id": 7,
"name": "Potter Mendez"
},
{
"user_id": 8,
"name": "Mallory Atkinson"
},
{
"user_id": 9,
"name": "Sabrina Tanner"
},
{
"user_id": 10,
"name": "Guerrero Mccall"
},
{
"user_id": 11,
"name": "Collier Trujillo"
},
{
"user_id": 12,
"name": "Pope Rivers"
},
{
"user_id": 13,
"name": "Jackson Ellison"
},
{
"user_id": 14,
"name": "Mcintosh Sosa"
}
]
},
{
"user_id": 4,
"name": "Wolfe Glenn",
"children": [
{
"user_id": 0,
"name": "Santana Johns"
},
{
"user_id": 1,
"name": "Rosemarie Castro"
},
{
"user_id": 2,
"name": "Mason Hanson"
},
{
"user_id": 3,
"name": "Luann Carter"
},
{
"user_id": 4,
"name": "Cherry George"
},
{
"user_id": 5,
"name": "Kirsten Munoz"
},
{
"user_id": 6,
"name": "Jacquelyn Stevens"
},
{
"user_id": 7,
"name": "Pat Witt"
},
{
"user_id": 8,
"name": "Romero Dixon"
},
{
"user_id": 9,
"name": "Washington Hurst"
},
{
"user_id": 10,
"name": "Mueller Sharpe"
},
{
"user_id": 11,
"name": "Avis Mccarthy"
},
{
"user_id": 12,
"name": "Erma Slater"
},
{
"user_id": 13,
"name": "Imogene Pearson"
},
{
"user_id": 14,
"name": "Marquez Contreras"
}
]
},
{
"user_id": 5,
"name": "Bond Hampton",
"children": [
{
"user_id": 0,
"name": "Jenny Bowers"
},
{
"user_id": 1,
"name": "Meadows Pope"
},
{
"user_id": 2,
"name": "Beck Cruz"
},
{
"user_id": 3,
"name": "Barbara Mcmahon"
},
{
"user_id": 4,
"name": "Ashley Morales"
},
{
"user_id": 5,
"name": "Ernestine Hinton"
},
{
"user_id": 6,
"name": "Hawkins Castillo"
},
{
"user_id": 7,
"name": "Carey Rowe"
},
{
"user_id": 8,
"name": "Whitaker Norman"
},
{
"user_id": 9,
"name": "Inez Ellis"
},
{
"user_id": 10,
"name": "Shauna Bryan"
},
{
"user_id": 11,
"name": "White Lawson"
},
{
"user_id": 12,
"name": "Lynnette Ware"
},
{
"user_id": 13,
"name": "Clements Barton"
},
{
"user_id": 14,
"name": "Armstrong Moon"
}
]
},
{
"user_id": 6,
"name": "Marguerite Hensley",
"children": [
{
"user_id": 0,
"name": "Wise Knowles"
},
{
"user_id": 1,
"name": "Kristy Jordan"
},
{
"user_id": 2,
"name": "Hodge Wilder"
},
{
"user_id": 3,
"name": "Jewel Fuller"
},
{
"user_id": 4,
"name": "Horne Luna"
},
{
"user_id": 5,
"name": "Mamie Acevedo"
},
{
"user_id": 6,
"name": "Drake Holder"
},
{
"user_id": 7,
"name": "Silva Yang"
},
{
"user_id": 8,
"name": "Wiggins Rodgers"
},
{
"user_id": 9,
"name": "Tamara Cohen"
},
{
"user_id": 10,
"name": "Leslie Mayer"
},
{
"user_id": 11,
"name": "Georgia Daniels"
},
{
"user_id": 12,
"name": "Julie Hansen"
},
{
"user_id": 13,
"name": "Gail Mullen"
},
{
"user_id": 14,
"name": "Diane Cummings"
}
]
},
{
"user_id": 7,
"name": "Myrtle Bartlett",
"children": [
{
"user_id": 0,
"name": "Jones Harrison"
},
{
"user_id": 1,
"name": "Carlson Pugh"
},
{
"user_id": 2,
"name": "Browning Shaw"
},
{
"user_id": 3,
"name": "Rosario Lamb"
},
{
"user_id": 4,
"name": "Ramos Evans"
},
{
"user_id": 5,
"name": "Rosalyn Rowland"
},
{
"user_id": 6,
"name": "Kerr Gilliam"
},
{
"user_id": 7,
"name": "Madden Kline"
},
{
"user_id": 8,
"name": "Todd West"
},
{
"user_id": 9,
"name": "Gwen Foster"
},
{
"user_id": 10,
"name": "Maude Melendez"
},
{
"user_id": 11,
"name": "Hanson Jacobs"
},
{
"user_id": 12,
"name": "Foreman Parsons"
},
{
"user_id": 13,
"name": "Ericka Holden"
},
{
"user_id": 14,
"name": "Mckay Keller"
}
]
},
{
"user_id": 8,
"name": "Imelda Oliver",
"children": [
{
"user_id": 0,
"name": "Alana Levine"
},
{
"user_id": 1,
"name": "Navarro Hernandez"
},
{
"user_id": 2,
"name": "Kim Torres"
},
{
"user_id": 3,
"name": "Virgie Hawkins"
},
{
"user_id": 4,
"name": "Angela Vang"
},
{
"user_id": 5,
"name": "Kellie Yates"
},
{
"user_id": 6,
"name": "Lenora Rodriguez"
},
{
"user_id": 7,
"name": "Cameron Burch"
},
{
"user_id": 8,
"name": "Chris Huffman"
},
{
"user_id": 9,
"name": "Reyna Gillespie"
},
{
"user_id": 10,
"name": "Sheila Richardson"
},
{
"user_id": 11,
"name": "Sutton Maddox"
},
{
"user_id": 12,
"name": "Salas Cross"
},
{
"user_id": 13,
"name": "Miranda Clarke"
},
{
"user_id": 14,
"name": "Sheppard Wynn"
}
]
},
{
"user_id": 9,
"name": "Martinez Walsh",
"children": [
{
"user_id": 0,
"name": "Bettye Romero"
},
{
"user_id": 1,
"name": "Michelle Avery"
},
{
"user_id": 2,
"name": "Oneil Pacheco"
},
{
"user_id": 3,
"name": "Hicks Sloan"
},
{
"user_id": 4,
"name": "Caldwell Woodward"
},
{
"user_id": 5,
"name": "Booker Finch"
},
{
"user_id": 6,
"name": "Shawna Mckee"
},
{
"user_id": 7,
"name": "Delia Olson"
},
{
"user_id": 8,
"name": "Nina Crawford"
},
{
"user_id": 9,
"name": "Marcie Whitley"
},
{
"user_id": 10,
"name": "Lewis Morin"
},
{
"user_id": 11,
"name": "Liz Parrish"
},
{
"user_id": 12,
"name": "Adrian Lynch"
},
{
"user_id": 13,
"name": "Massey Nash"
},
{
"user_id": 14,
"name": "Victoria Vance"
}
]
},
{
"user_id": 10,
"name": "Rosella Ramsey",
"children": [
{
"user_id": 0,
"name": "Hillary Hyde"
},
{
"user_id": 1,
"name": "Flossie Gentry"
},
{
"user_id": 2,
"name": "Atkins Huber"
},
{
"user_id": 3,
"name": "Lowe Brennan"
},
{
"user_id": 4,
"name": "Hale Melton"
},
{
"user_id": 5,
"name": "Betty Ball"
},
{
"user_id": 6,
"name": "Compton Nixon"
},
{
"user_id": 7,
"name": "Jacobs Sanchez"
},
{
"user_id": 8,
"name": "Campbell Cochran"
},
{
"user_id": 9,
"name": "Dorsey Hubbard"
},
{
"user_id": 10,
"name": "Ramona Tucker"
},
{
"user_id": 11,
"name": "Weaver Jacobson"
},
{
"user_id": 12,
"name": "Wade Cantu"
},
{
"user_id": 13,
"name": "Harvey Collins"
},
{
"user_id": 14,
"name": "Marisa Harmon"
}
]
},
{
"user_id": 11,
"name": "Randolph Humphrey",
"children": [
{
"user_id": 0,
"name": "Dora Warner"
},
{
"user_id": 1,
"name": "Adriana Richmond"
},
{
"user_id": 2,
"name": "Lelia Macdonald"
},
{
"user_id": 3,
"name": "Elma Bean"
},
{
"user_id": 4,
"name": "Richards Park"
},
{
"user_id": 5,
"name": "Lara Weber"
},
{
"user_id": 6,
"name": "Puckett Delacruz"
},
{
"user_id": 7,
"name": "Lakisha Day"
},
{
"user_id": 8,
"name": "Goodman Palmer"
},
{
"user_id": 9,
"name": "Lina Newton"
},
{
"user_id": 10,
"name": "Jeannette Oneill"
},
{
"user_id": 11,
"name": "Ray Sears"
},
{
"user_id": 12,
"name": "Mooney Pierce"
},
{
"user_id": 13,
"name": "Clay Randolph"
},
{
"user_id": 14,
"name": "Denise Savage"
}
]
},
{
"user_id": 12,
"name": "Carey Arnold",
"children": [
{
"user_id": 0,
"name": "Cooper Scott"
},
{
"user_id": 1,
"name": "Edwina Rosario"
},
{
"user_id": 2,
"name": "Cassie Butler"
},
{
"user_id": 3,
"name": "Hogan Buckley"
},
{
"user_id": 4,
"name": "Betsy Reed"
},
{
"user_id": 5,
"name": "Beasley Schneider"
},
{
"user_id": 6,
"name": "Luella Walker"
},
{
"user_id": 7,
"name": "Woodard Avila"
},
{
"user_id": 8,
"name": "Dominique Wise"
},
{
"user_id": 9,
"name": "Wendi Burns"
},
{
"user_id": 10,
"name": "Dana Copeland"
},
{
"user_id": 11,
"name": "Martina Hickman"
},
{
"user_id": 12,
"name": "Mcclain Powell"
},
{
"user_id": 13,
"name": "Woods Hahn"
},
{
"user_id": 14,
"name": "Sloan Reid"
}
]
},
{
"user_id": 13,
"name": "Latasha Waller",
"children": [
{
"user_id": 0,
"name": "Parks Murray"
},
{
"user_id": 1,
"name": "Rowena Taylor"
},
{
"user_id": 2,
"name": "Alford Vincent"
},
{
"user_id": 3,
"name": "Gena Cote"
},
{
"user_id": 4,
"name": "Wilkins Solomon"
},
{
"user_id": 5,
"name": "Gallagher Barnett"
},
{
"user_id": 6,
"name": "Darla Spencer"
},
{
"user_id": 7,
"name": "Stokes Calhoun"
},
{
"user_id": 8,
"name": "Wallace Moore"
},
{
"user_id": 9,
"name": "Barnes White"
},
{
"user_id": 10,
"name": "Bridges English"
},
{
"user_id": 11,
"name": "Lindsey Hester"
},
{
"user_id": 12,
"name": "Marsh Guerrero"
},
{
"user_id": 13,
"name": "Williamson Noble"
},
{
"user_id": 14,
"name": "Lavonne Nelson"
}
]
},
{
"user_id": 14,
"name": "Blanca Holmes",
"children": [
{
"user_id": 0,
"name": "Cynthia Tran"
},
{
"user_id": 1,
"name": "Tamra Carver"
},
{
"user_id": 2,
"name": "Oconnor Acosta"
},
{
"user_id": 3,
"name": "Maxine Ratliff"
},
{
"user_id": 4,
"name": "Lindsay Cannon"
},
{
"user_id": 5,
"name": "Carney Harrington"
},
{
"user_id": 6,
"name": "Millie Roach"
},
{
"user_id": 7,
"name": "Waters Odom"
},
{
"user_id": 8,
"name": "Heidi Gill"
},
{
"user_id": 9,
"name": "Gracie Guzman"
},
{
"user_id": 10,
"name": "Grant Mack"
},
{
"user_id": 11,
"name": "Rosalinda Webb"
},
{
"user_id": 12,
"name": "Jarvis Whitfield"
},
{
"user_id": 13,
"name": "Veronica Stein"
},
{
"user_id": 14,
"name": "Harmon Kidd"
}
]
}
]
}
]
},
{
"user_id": 1,
"name": "Constance Prince",
"children": [
{
"user_id": 1,
"name": "Faith Phelps",
"children": [
{
"user_id": 0,
"name": "Mcgowan Fernandez",
"children": [
{
"user_id": 0,
"name": "Rollins Joyce"
},
{
"user_id": 1,
"name": "Shawna Ortiz"
},
{
"user_id": 2,
"name": "Dorothy Frank"
},
{
"user_id": 3,
"name": "Wyatt Hays"
},
{
"user_id": 4,
"name": "Barrett Haney"
},
{
"user_id": 5,
"name": "Francesca Kinney"
},
{
"user_id": 6,
"name": "Brady Cohen"
},
{
"user_id": 7,
"name": "Tanner Lloyd"
},
{
"user_id": 8,
"name": "Adkins Page"
},
{
"user_id": 9,
"name": "Janette Anthony"
},
{
"user_id": 10,
"name": "Alberta Solomon"
},
{
"user_id": 11,
"name": "Stout Santana"
},
{
"user_id": 12,
"name": "Stuart Decker"
},
{
"user_id": 13,
"name": "Oconnor Wallace"
},
{
"user_id": 14,
"name": "Wendy Farrell"
}
]
},
{
"user_id": 1,
"name": "Pickett Sherman",
"children": [
{
"user_id": 0,
"name": "Vang Salinas"
},
{
"user_id": 1,
"name": "Alvarado Sanchez"
},
{
"user_id": 2,
"name": "Hanson Giles"
},
{
"user_id": 3,
"name": "Eloise Miranda"
},
{
"user_id": 4,
"name": "May Douglas"
},
{
"user_id": 5,
"name": "Johanna Ellis"
},
{
"user_id": 6,
"name": "Irma Chang"
},
{
"user_id": 7,
"name": "Violet Horn"
},
{
"user_id": 8,
"name": "Christi Townsend"
},
{
"user_id": 9,
"name": "Jerry Patrick"
},
{
"user_id": 10,
"name": "Morrison Morales"
},
{
"user_id": 11,
"name": "Terrell Schneider"
},
{
"user_id": 12,
"name": "Katherine Blair"
},
{
"user_id": 13,
"name": "Walters Dean"
},
{
"user_id": 14,
"name": "Penelope Hinton"
}
]
},
{
"user_id": 2,
"name": "Jerri Evans",
"children": [
{
"user_id": 0,
"name": "Dawson Levine"
},
{
"user_id": 1,
"name": "Tracie Levy"
},
{
"user_id": 2,
"name": "Walton Kidd"
},
{
"user_id": 3,
"name": "Mueller Sykes"
},
{
"user_id": 4,
"name": "Knapp Hunt"
},
{
"user_id": 5,
"name": "Hoover Rojas"
},
{
"user_id": 6,
"name": "Iva Hernandez"
},
{
"user_id": 7,
"name": "Irene Blankenship"
},
{
"user_id": 8,
"name": "Sosa Ochoa"
},
{
"user_id": 9,
"name": "Knight Black"
},
{
"user_id": 10,
"name": "Olivia Peters"
},
{
"user_id": 11,
"name": "Fernandez Fletcher"
},
{
"user_id": 12,
"name": "Jamie Underwood"
},
{
"user_id": 13,
"name": "Montoya Hartman"
},
{
"user_id": 14,
"name": "Rosemary Castro"
}
]
},
{
"user_id": 3,
"name": "Hurley Dunn",
"children": [
{
"user_id": 0,
"name": "Rodgers Ellison"
},
{
"user_id": 1,
"name": "Richard Whitney"
},
{
"user_id": 2,
"name": "Haley Boyle"
},
{
"user_id": 3,
"name": "Jefferson Brown"
},
{
"user_id": 4,
"name": "Stacey Brock"
},
{
"user_id": 5,
"name": "Melba House"
},
{
"user_id": 6,
"name": "Charles Frost"
},
{
"user_id": 7,
"name": "Schmidt Holcomb"
},
{
"user_id": 8,
"name": "Liz Martinez"
},
{
"user_id": 9,
"name": "Summers Estrada"
},
{
"user_id": 10,
"name": "Pittman Lawson"
},
{
"user_id": 11,
"name": "Whitfield Dennis"
},
{
"user_id": 12,
"name": "Travis Chapman"
},
{
"user_id": 13,
"name": "Amy Hester"
},
{
"user_id": 14,
"name": "Willie Davidson"
}
]
},
{
"user_id": 4,
"name": "Shelia Rogers",
"children": [
{
"user_id": 0,
"name": "Knox Ferguson"
},
{
"user_id": 1,
"name": "Hansen Carey"
},
{
"user_id": 2,
"name": "Misty Weber"
},
{
"user_id": 3,
"name": "Diane Peterson"
},
{
"user_id": 4,
"name": "Gracie Yang"
},
{
"user_id": 5,
"name": "Campos Bradford"
},
{
"user_id": 6,
"name": "Jo Cabrera"
},
{
"user_id": 7,
"name": "Angie Compton"
},
{
"user_id": 8,
"name": "Chase Miles"
},
{
"user_id": 9,
"name": "Donaldson Pittman"
},
{
"user_id": 10,
"name": "Reba Vance"
},
{
"user_id": 11,
"name": "Dominique Blackwell"
},
{
"user_id": 12,
"name": "Mildred Tillman"
},
{
"user_id": 13,
"name": "Obrien Fields"
},
{
"user_id": 14,
"name": "Margret Hebert"
}
]
},
{
"user_id": 5,
"name": "Mann Nolan",
"children": [
{
"user_id": 0,
"name": "Earline Ayers"
},
{
"user_id": 1,
"name": "Eddie Davenport"
},
{
"user_id": 2,
"name": "Alana Mann"
},
{
"user_id": 3,
"name": "Rosanna Norris"
},
{
"user_id": 4,
"name": "Fisher Gray"
},
{
"user_id": 5,
"name": "Rowland Velazquez"
},
{
"user_id": 6,
"name": "Nanette Dawson"
},
{
"user_id": 7,
"name": "Maureen Murray"
},
{
"user_id": 8,
"name": "Ashley Joseph"
},
{
"user_id": 9,
"name": "Bonner Mercado"
},
{
"user_id": 10,
"name": "Elise Woodward"
},
{
"user_id": 11,
"name": "Bianca Colon"
},
{
"user_id": 12,
"name": "Johnson Gilbert"
},
{
"user_id": 13,
"name": "Dixon Neal"
},
{
"user_id": 14,
"name": "Karen Thornton"
}
]
},
{
"user_id": 6,
"name": "Vaughn Guthrie",
"children": [
{
"user_id": 0,
"name": "Henrietta Norman"
},
{
"user_id": 1,
"name": "Maldonado Peck"
},
{
"user_id": 2,
"name": "Pitts Snider"
},
{
"user_id": 3,
"name": "Ingrid Simpson"
},
{
"user_id": 4,
"name": "Bridgett Pena"
},
{
"user_id": 5,
"name": "Adams Davis"
},
{
"user_id": 6,
"name": "Larson Petersen"
},
{
"user_id": 7,
"name": "Goldie Strong"
},
{
"user_id": 8,
"name": "Sandy Hood"
},
{
"user_id": 9,
"name": "Garrison Knapp"
},
{
"user_id": 10,
"name": "Leann Hickman"
},
{
"user_id": 11,
"name": "Franco Fischer"
},
{
"user_id": 12,
"name": "Tabitha Sawyer"
},
{
"user_id": 13,
"name": "Porter Willis"
},
{
"user_id": 14,
"name": "Chan Floyd"
}
]
},
{
"user_id": 7,
"name": "Wood Schroeder",
"children": [
{
"user_id": 0,
"name": "Yesenia Rice"
},
{
"user_id": 1,
"name": "Sharon Vaughn"
},
{
"user_id": 2,
"name": "Ward Fuentes"
},
{
"user_id": 3,
"name": "Reese Adkins"
},
{
"user_id": 4,
"name": "Henderson Brooks"
},
{
"user_id": 5,
"name": "Davidson Pope"
},
{
"user_id": 6,
"name": "Toni Richardson"
},
{
"user_id": 7,
"name": "Colleen Atkins"
},
{
"user_id": 8,
"name": "Webster Gilliam"
},
{
"user_id": 9,
"name": "Muriel Goodman"
},
{
"user_id": 10,
"name": "Hooper Daniels"
},
{
"user_id": 11,
"name": "Farrell Rivera"
},
{
"user_id": 12,
"name": "Rae Wiley"
},
{
"user_id": 13,
"name": "Abigail Williamson"
},
{
"user_id": 14,
"name": "Kline Benton"
}
]
},
{
"user_id": 8,
"name": "Joan Ryan",
"children": [
{
"user_id": 0,
"name": "Kelley Carney"
},
{
"user_id": 1,
"name": "Tiffany Nicholson"
},
{
"user_id": 2,
"name": "Brennan Casey"
},
{
"user_id": 3,
"name": "Neal Osborn"
},
{
"user_id": 4,
"name": "Miranda Dodson"
},
{
"user_id": 5,
"name": "Thompson Mcfarland"
},
{
"user_id": 6,
"name": "Fleming Rutledge"
},
{
"user_id": 7,
"name": "Bernadette Jacobson"
},
{
"user_id": 8,
"name": "Petra Hicks"
},
{
"user_id": 9,
"name": "Marquez Michael"
},
{
"user_id": 10,
"name": "Donovan Bryan"
},
{
"user_id": 11,
"name": "Hope Morton"
},
{
"user_id": 12,
"name": "Elvira Cotton"
},
{
"user_id": 13,
"name": "Frankie Tran"
},
{
"user_id": 14,
"name": "Guy Griffith"
}
]
},
{
"user_id": 9,
"name": "Talley Simmons",
"children": [
{
"user_id": 0,
"name": "Bass Mcdowell"
},
{
"user_id": 1,
"name": "Ofelia Montoya"
},
{
"user_id": 2,
"name": "Agnes Nelson"
},
{
"user_id": 3,
"name": "Tamera Hill"
},
{
"user_id": 4,
"name": "Miranda Ruiz"
},
{
"user_id": 5,
"name": "Mcdaniel Barnett"
},
{
"user_id": 6,
"name": "Rich Bean"
},
{
"user_id": 7,
"name": "Hines Griffin"
},
{
"user_id": 8,
"name": "Erna Farley"
},
{
"user_id": 9,
"name": "Burgess Scott"
},
{
"user_id": 10,
"name": "Chris Howe"
},
{
"user_id": 11,
"name": "Tammie Cline"
},
{
"user_id": 12,
"name": "Booth Sexton"
},
{
"user_id": 13,
"name": "Harper Durham"
},
{
"user_id": 14,
"name": "Dollie May"
}
]
},
{
"user_id": 10,
"name": "Alicia Glass",
"children": [
{
"user_id": 0,
"name": "Cheryl Conrad"
},
{
"user_id": 1,
"name": "Patti Miller"
},
{
"user_id": 2,
"name": "Neva Mcgowan"
},
{
"user_id": 3,
"name": "Hutchinson Whitehead"
},
{
"user_id": 4,
"name": "Kate Vaughn"
},
{
"user_id": 5,
"name": "Hogan Barrett"
},
{
"user_id": 6,
"name": "Tami Conway"
},
{
"user_id": 7,
"name": "Michael Velez"
},
{
"user_id": 8,
"name": "Cornelia Brewer"
},
{
"user_id": 9,
"name": "Thompson Watkins"
},
{
"user_id": 10,
"name": "Morrow Cabrera"
},
{
"user_id": 11,
"name": "Rose Berg"
},
{
"user_id": 12,
"name": "Case Kerr"
},
{
"user_id": 13,
"name": "Imelda Rivas"
},
{
"user_id": 14,
"name": "Frances Wyatt"
}
]
},
{
"user_id": 11,
"name": "Weaver Beck",
"children": [
{
"user_id": 0,
"name": "Kimberly Osborne"
},
{
"user_id": 1,
"name": "Hannah Carey"
},
{
"user_id": 2,
"name": "Emily Mcintyre"
},
{
"user_id": 3,
"name": "Melba Horn"
},
{
"user_id": 4,
"name": "Serena Perez"
},
{
"user_id": 5,
"name": "Johnnie Holder"
},
{
"user_id": 6,
"name": "Wiggins Greer"
},
{
"user_id": 7,
"name": "Weiss Peters"
},
{
"user_id": 8,
"name": "Barrett Rutledge"
},
{
"user_id": 9,
"name": "Burris Hebert"
},
{
"user_id": 10,
"name": "Chrystal Vasquez"
},
{
"user_id": 11,
"name": "Zamora Rodriquez"
},
{
"user_id": 12,
"name": "Laurie Benjamin"
},
{
"user_id": 13,
"name": "Alice Rodgers"
},
{
"user_id": 14,
"name": "Susie Blankenship"
}
]
},
{
"user_id": 12,
"name": "Lindsay Cohen",
"children": [
{
"user_id": 0,
"name": "Sanders Shaw"
},
{
"user_id": 1,
"name": "Clay Madden"
},
{
"user_id": 2,
"name": "Sheena Merrill"
},
{
"user_id": 3,
"name": "Kris Graham"
},
{
"user_id": 4,
"name": "Adrian Morales"
},
{
"user_id": 5,
"name": "Vickie Everett"
},
{
"user_id": 6,
"name": "Abbott Calhoun"
},
{
"user_id": 7,
"name": "Hayes Leonard"
},
{
"user_id": 8,
"name": "Gould Brock"
},
{
"user_id": 9,
"name": "Vinson Fowler"
},
{
"user_id": 10,
"name": "Chambers Howell"
},
{
"user_id": 11,
"name": "Darla Bradshaw"
},
{
"user_id": 12,
"name": "Nancy Marshall"
},
{
"user_id": 13,
"name": "Leann Harper"
},
{
"user_id": 14,
"name": "Cindy Wilcox"
}
]
},
{
"user_id": 13,
"name": "Glenda Dickerson",
"children": [
{
"user_id": 0,
"name": "Melanie Reyes"
},
{
"user_id": 1,
"name": "Ada Rhodes"
},
{
"user_id": 2,
"name": "Ursula Santos"
},
{
"user_id": 3,
"name": "Lesley Gibson"
},
{
"user_id": 4,
"name": "Frazier Gillespie"
},
{
"user_id": 5,
"name": "Rosanne Clayton"
},
{
"user_id": 6,
"name": "Noemi Carver"
},
{
"user_id": 7,
"name": "Young Massey"
},
{
"user_id": 8,
"name": "King Hutchinson"
},
{
"user_id": 9,
"name": "Sharron Patterson"
},
{
"user_id": 10,
"name": "Browning Gates"
},
{
"user_id": 11,
"name": "Renee Vance"
},
{
"user_id": 12,
"name": "Kristina Wheeler"
},
{
"user_id": 13,
"name": "Bowers Macdonald"
},
{
"user_id": 14,
"name": "Russo Cross"
}
]
},
{
"user_id": 14,
"name": "Sykes Rosa",
"children": [
{
"user_id": 0,
"name": "Sellers Ingram"
},
{
"user_id": 1,
"name": "Marietta Shelton"
},
{
"user_id": 2,
"name": "Cummings Carroll"
},
{
"user_id": 3,
"name": "Lucas Reilly"
},
{
"user_id": 4,
"name": "Jane Hester"
},
{
"user_id": 5,
"name": "Amanda Walsh"
},
{
"user_id": 6,
"name": "Christian Sanchez"
},
{
"user_id": 7,
"name": "Audrey Alexander"
},
{
"user_id": 8,
"name": "Emma Park"
},
{
"user_id": 9,
"name": "Angelita Vang"
},
{
"user_id": 10,
"name": "Shawna Bray"
},
{
"user_id": 11,
"name": "Herring Pena"
},
{
"user_id": 12,
"name": "Wilma Dixon"
},
{
"user_id": 13,
"name": "Jerri Kemp"
},
{
"user_id": 14,
"name": "Rush Price"
}
]
}
]
},
{
"user_id": 2,
"name": "Young Levine",
"children": [
{
"user_id": 5,
"name": "Chaney Bell",
"children": [
{
"user_id": 0,
"name": "Elma Bass"
},
{
"user_id": 1,
"name": "Marylou Guy"
},
{
"user_id": 2,
"name": "Brooke Baird"
},
{
"user_id": 3,
"name": "Kathryn Stout"
},
{
"user_id": 4,
"name": "Holman Pugh"
},
{
"user_id": 5,
"name": "Lawson Blackwell"
},
{
"user_id": 6,
"name": "Lily Strong"
},
{
"user_id": 7,
"name": "Sharon Duffy"
},
{
"user_id": 8,
"name": "Bennett Cook"
},
{
"user_id": 9,
"name": "Ines Conley"
},
{
"user_id": 10,
"name": "Ross Reid"
},
{
"user_id": 11,
"name": "Leach Pratt"
},
{
"user_id": 12,
"name": "Lilly Cole"
},
{
"user_id": 13,
"name": "Schultz Hart"
},
{
"user_id": 14,
"name": "Gilbert Gilbert"
}
]
},
{
"user_id": 11,
"name": "Carey Odonnell",
"children": [
{
"user_id": 0,
"name": "Robinson Vazquez"
},
{
"user_id": 1,
"name": "Mandy Wise"
},
{
"user_id": 2,
"name": "Mcclain Sanford"
},
{
"user_id": 3,
"name": "Taylor Wooten"
},
{
"user_id": 4,
"name": "Weber Best"
},
{
"user_id": 5,
"name": "Cecelia Henson"
},
{
"user_id": 6,
"name": "Rhonda Baker"
},
{
"user_id": 7,
"name": "Cara Gregory"
},
{
"user_id": 8,
"name": "James Walter"
},
{
"user_id": 9,
"name": "Christa Roth"
},
{
"user_id": 10,
"name": "Stevenson Rodriguez"
},
{
"user_id": 11,
"name": "Johanna Cummings"
},
{
"user_id": 12,
"name": "Vanessa Collins"
},
{
"user_id": 13,
"name": "Davidson Meyer"
},
{
"user_id": 14,
"name": "Peggy King"
}
]
},
{
"user_id": 13,
"name": "Anna Forbes",
"children": [
{
"user_id": 0,
"name": "Jeanne Romero"
},
{
"user_id": 1,
"name": "Kelley Keller"
},
{
"user_id": 2,
"name": "Kaitlin Mathis"
},
{
"user_id": 3,
"name": "Gordon Keith"
},
{
"user_id": 4,
"name": "Mavis Parker"
},
{
"user_id": 5,
"name": "Dejesus Walls"
},
{
"user_id": 6,
"name": "Ratliff Shaffer"
},
{
"user_id": 7,
"name": "Maryellen Gomez"
},
{
"user_id": 8,
"name": "Hudson Christian"
},
{
"user_id": 9,
"name": "Natalia Bond"
},
{
"user_id": 10,
"name": "Newton Pitts"
},
{
"user_id": 11,
"name": "Matilda Rivera"
},
{
"user_id": 12,
"name": "Palmer Pickett"
},
{
"user_id": 13,
"name": "Bradley Mckinney"
},
{
"user_id": 14,
"name": "Shelia Galloway"
}
]
}
]
}
]
}
]
};
// Get JSON data
//treeJSON = d3.json('hey', function(error, treeData) {
// Calculate total nodes, max label length
var totalNodes = 0;
var maxLabelLength = 0;
// variables for drag/drop
var selectedNode = null;
var draggingNode = null;
// panning variables
var panSpeed = 200;
var panBoundary = 20; // Within 20px from edges will pan when dragging.
// Misc. variables
var i = 0;
var duration = 750;
var root;
// size of the diagram
var viewerWidth = $(document).width();
var viewerHeight = $(document).height();
var tree = d3.layout.tree()
.size([viewerHeight, viewerWidth]);
// define a d3 diagonal projection for use by the node paths later on.
var diagonal = d3.svg.diagonal()
.projection(function(d) {
return [d.y, d.x];
});
// A recursive helper function for performing some setup by walking through all nodes
function visit(parent, visitFn, childrenFn) {
if (!parent) return;
visitFn(parent);
var children = childrenFn(parent);
if (children) {
var count = children.length;
for (var i = 0; i < count; i++) {
visit(children[i], visitFn, childrenFn);
}
}
}
// Call visit function to establish maxLabelLength
visit(treeData, function(d) {
totalNodes++;
console.log(d);
maxLabelLength = 10;
console.log("after");
}, function(d) {
return d.children && d.children.length > 0 ? d.children : null;
});
// sort the tree according to the node names
function sortTree() {
tree.sort(function(a, b) {
if (b.name !== undefined && a.name !== undefined) {
return b.name.toLowerCase() < a.name.toLowerCase() ? 1 : -1;
} else {
return 100000;
}
});
}
// Sort the tree initially incase the JSON isn't in a sorted order.
sortTree();
// TODO: Pan function, can be better implemented.
function pan(domNode, direction) {
var speed = panSpeed;
if (panTimer) {
clearTimeout(panTimer);
translateCoords = d3.transform(svgGroup.attr("transform"));
if (direction == 'left' || direction == 'right') {
translateX = direction == 'left' ? translateCoords.translate[0] + speed : translateCoords.translate[0] - speed;
translateY = translateCoords.translate[1];
} else if (direction == 'up' || direction == 'down') {
translateX = translateCoords.translate[0];
translateY = direction == 'up' ? translateCoords.translate[1] + speed : translateCoords.translate[1] - speed;
}
scaleX = translateCoords.scale[0];
scaleY = translateCoords.scale[1];
scale = zoomListener.scale();
svgGroup.transition().attr("transform", "translate(" + translateX + "," + translateY + ")scale(" + scale + ")");
d3.select(domNode).select('g.node').attr("transform", "translate(" + translateX + "," + translateY + ")");
zoomListener.scale(zoomListener.scale());
zoomListener.translate([translateX, translateY]);
panTimer = setTimeout(function() {
pan(domNode, speed, direction);
}, 50);
}
}
// Define the zoom function for the zoomable tree
function zoom() {
svgGroup.attr("transform", "translate(" + d3.event.translate + ")scale(" + d3.event.scale + ")");
}
// define the zoomListener which calls the zoom function on the "zoom" event constrained within the scaleExtents
var zoomListener = d3.behavior.zoom().scaleExtent([0.1, 3]).on("zoom", zoom);
function initiateDrag(d, domNode) {
draggingNode = d;
d3.select(domNode).select('.ghostCircle').attr('pointer-events', 'none');
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle show');
d3.select(domNode).attr('class', 'node activeDrag');
svgGroup.selectAll("g.node").sort(function(a, b) { // select the parent and sort the path's
if (a.id != draggingNode.id) return 1; // a is not the hovered element, send "a" to the back
else return -1; // a is the hovered element, bring "a" to the front
});
// if nodes has children, remove the links and nodes
if (nodes.length > 1) {
// remove link paths
links = tree.links(nodes);
nodePaths = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
}).remove();
// remove child nodes
nodesExit = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id;
}).filter(function(d, i) {
if (d.id == draggingNode.id) {
return false;
}
return true;
}).remove();
}
// remove parent link
parentLink = tree.links(tree.nodes(draggingNode.parent));
svgGroup.selectAll('path.link').filter(function(d, i) {
if (d.target.id == draggingNode.id) {
return true;
}
return false;
}).remove();
dragStarted = null;
}
// define the baseSvg, attaching a class for styling and the zoomListener
var baseSvg = d3.select("#tree-container").append("svg")
.attr("width", viewerWidth)
.attr("height", viewerHeight)
.attr("class", "overlay")
.call(zoomListener);
// Define the drag listeners for drag/drop behaviour of nodes.
dragListener = d3.behavior.drag()
.on("dragstart", function(d) {
if (d == root) {
return;
}
dragStarted = true;
nodes = tree.nodes(d);
d3.event.sourceEvent.stopPropagation();
// it's important that we suppress the mouseover event on the node being dragged. Otherwise it will absorb the mouseover event and the underlying node will not detect it d3.select(this).attr('pointer-events', 'none');
})
.on("drag", function(d) {
if (d == root) {
return;
}
if (dragStarted) {
domNode = this;
initiateDrag(d, domNode);
}
// get coords of mouseEvent relative to svg container to allow for panning
relCoords = d3.mouse($('svg').get(0));
if (relCoords[0] < panBoundary) {
panTimer = true;
pan(this, 'left');
} else if (relCoords[0] > ($('svg').width() - panBoundary)) {
panTimer = true;
pan(this, 'right');
} else if (relCoords[1] < panBoundary) {
panTimer = true;
pan(this, 'up');
} else if (relCoords[1] > ($('svg').height() - panBoundary)) {
panTimer = true;
pan(this, 'down');
} else {
try {
clearTimeout(panTimer);
} catch (e) {
}
}
d.x0 += d3.event.dy;
d.y0 += d3.event.dx;
var node = d3.select(this);
node.attr("transform", "translate(" + d.y0 + "," + d.x0 + ")");
updateTempConnector();
}).on("dragend", function(d) {
if (d == root) {
return;
}
domNode = this;
if (selectedNode) {
// now remove the element from the parent, and insert it into the new elements children
var index = draggingNode.parent.children.indexOf(draggingNode);
if (index > -1) {
draggingNode.parent.children.splice(index, 1);
}
if (typeof selectedNode.children !== 'undefined' || typeof selectedNode._children !== 'undefined') {
if (typeof selectedNode.children !== 'undefined') {
selectedNode.children.push(draggingNode);
} else {
selectedNode._children.push(draggingNode);
}
} else {
selectedNode.children = [];
selectedNode.children.push(draggingNode);
}
// Make sure that the node being added to is expanded so user can see added node is correctly moved
expand(selectedNode);
sortTree();
endDrag();
} else {
endDrag();
}
});
function endDrag() {
selectedNode = null;
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle');
d3.select(domNode).attr('class', 'node');
// now restore the mouseover event or we won't be able to drag a 2nd time
d3.select(domNode).select('.ghostCircle').attr('pointer-events', '');
updateTempConnector();
if (draggingNode !== null) {
update(root);
centerNode(draggingNode);
draggingNode = null;
}
}
// Helper functions for collapsing and expanding nodes.
function collapse(d) {
if (d.children) {
d._children = d.children;
d._children.forEach(collapse);
d.children = null;
}
}
function expand(d) {
if (d._children) {
d.children = d._children;
d.children.forEach(expand);
d._children = null;
}
}
var overCircle = function(d) {
selectedNode = d;
updateTempConnector();
};
var outCircle = function(d) {
selectedNode = null;
updateTempConnector();
};
// Function to update the temporary connector indicating dragging affiliation
var updateTempConnector = function() {
var data = [];
if (draggingNode !== null && selectedNode !== null) {
// have to flip the source coordinates since we did this for the existing connectors on the original tree
data = [{
source: {
x: selectedNode.y0,
y: selectedNode.x0
},
target: {
x: draggingNode.y0,
y: draggingNode.x0
}
}];
}
var link = svgGroup.selectAll(".templink").data(data);
link.enter().append("path")
.attr("class", "templink")
.attr("d", d3.svg.diagonal())
.attr('pointer-events', 'none');
link.attr("d", d3.svg.diagonal());
link.exit().remove();
};
// Function to center node when clicked/dropped so node doesn't get lost when collapsing/moving with large amount of children.
function centerNode(source) {
scale = zoomListener.scale();
x = -source.y0;
y = -source.x0;
x = x * scale + viewerWidth / 2;
y = y * scale + viewerHeight / 2;
d3.select('g').transition()
.duration(duration)
.attr("transform", "translate(" + x + "," + y + ")scale(" + scale + ")");
zoomListener.scale(scale);
zoomListener.translate([x, y]);
}
// Toggle children function
function toggleChildren(d) {
if (d.children) {
d._children = d.children;
d.children = null;
} else if (d._children) {
d.children = d._children;
d._children = null;
}
return d;
}
// Toggle children on click.
function click(d) {
if (d3.event.defaultPrevented) return; // click suppressed
d = toggleChildren(d);
update(d);
centerNode(d);
}
function update(source) {
// Compute the new height, function counts total children of root node and sets tree height accordingly.
// This prevents the layout looking squashed when new nodes are made visible or looking sparse when nodes are removed
// This makes the layout more consistent.
var levelWidth = [1];
var childCount = function(level, n) {
if (n.children && n.children.length > 0) {
if (levelWidth.length <= level + 1) levelWidth.push(0);
levelWidth[level + 1] += n.children.length;
n.children.forEach(function(d) {
childCount(level + 1, d);
});
}
};
childCount(0, root);
var newHeight = d3.max(levelWidth) * 25; // 25 pixels per line
tree = tree.size([newHeight, viewerWidth]);
// Compute the new tree layout.
var nodes = tree.nodes(root).reverse(),
links = tree.links(nodes);
// Set widths between levels based on maxLabelLength.
nodes.forEach(function(d) {
d.y = (d.depth * (maxLabelLength * 10)); //maxLabelLength * 10px
// alternatively to keep a fixed scale one can set a fixed depth per level
// Normalize for fixed-depth by commenting out below line
// d.y = (d.depth * 500); //500px per level.
});
// Update the nodes…
node = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id || (d.id = ++i);
});
// Enter any new nodes at the parent's previous position.
var nodeEnter = node.enter().append("g")
.call(dragListener)
.attr("class", "node")
.attr("transform", function(d) {
return "translate(" + source.y0 + "," + source.x0 + ")";
})
.on('click', click);
nodeEnter.append("circle")
.attr('class', 'nodeCircle')
.attr("r", 0)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
nodeEnter.append("text")
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("dy", ".35em")
.attr('class', 'nodeText')
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
})
.style("fill-opacity", 0);
// phantom node to give us mouseover in a radius around it
nodeEnter.append("circle")
.attr('class', 'ghostCircle')
.attr("r", 30)
.attr("opacity", 0.2) // change this to zero to hide the target area
.style("fill", "red")
.attr('pointer-events', 'mouseover')
.on("mouseover", function(node) {
overCircle(node);
})
.on("mouseout", function(node) {
outCircle(node);
});
// Update the text to reflect whether node has children or not.
node.select('text')
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
});
// Change the circle fill depending on whether it has children and is collapsed
node.select("circle.nodeCircle")
.attr("r", 4.5)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
// Transition nodes to their new position.
var nodeUpdate = node.transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + d.y + "," + d.x + ")";
});
// Fade the text in
nodeUpdate.select("text")
.style("fill-opacity", 1);
// Transition exiting nodes to the parent's new position.
var nodeExit = node.exit().transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + source.y + "," + source.x + ")";
})
.remove();
nodeExit.select("circle")
.attr("r", 0);
nodeExit.select("text")
.style("fill-opacity", 0);
// Update the links…
var link = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
});
// Enter any new links at the parent's previous position.
link.enter().insert("path", "g")
.attr("class", "link")
.attr("d", function(d) {
var o = {
x: source.x0,
y: source.y0
};
return diagonal({
source: o,
target: o
});
});
// Transition links to their new position.
link.transition()
.duration(duration)
.attr("d", diagonal);
// Transition exiting nodes to the parent's new position.
link.exit().transition()
.duration(duration)
.attr("d", function(d) {
var o = {
x: source.x,
y: source.y
};
return diagonal({
source: o,
target: o
});
})
.remove();
// Stash the old positions for transition.
nodes.forEach(function(d) {
d.x0 = d.x;
d.y0 = d.y;
});
}
// Append a group which holds all nodes and which the zoom Listener can act upon.
var svgGroup = baseSvg.append("g");
// Define the root
root = treeData;
root.x0 = viewerHeight / 2;
root.y0 = 0;
// Collapse all children of roots children before rendering.
root.children.forEach(function(child){
collapse(child);
});
// Layout the tree initially and center on the root node.
update(root);
centerNode(root);
//});
</script>
<script id="jsbin-source-javascript" type="text/javascript">var treeData = {
"user_id": 0,
"name": "Root Node",
"children": [
{
"user_id": 0,
"name": "Flossie Hickman",
"children": [
{
"user_id": 0,
"name": "Violet Arnold",
"children": [
{
"user_id": 4,
"name": "Sabrina Harrell",
"children": [
{
"user_id": 0,
"name": "Dalton Norman"
},
{
"user_id": 1,
"name": "Barrett Morales"
},
{
"user_id": 2,
"name": "Daniels Booth"
},
{
"user_id": 3,
"name": "Maxwell Rich"
},
{
"user_id": 4,
"name": "Bennett Washington"
},
{
"user_id": 5,
"name": "Lelia Banks"
},
{
"user_id": 6,
"name": "Georgette Joyce"
},
{
"user_id": 7,
"name": "Kaitlin Irwin"
},
{
"user_id": 8,
"name": "Lacey Case"
},
{
"user_id": 9,
"name": "Reyes Jenkins"
},
{
"user_id": 10,
"name": "Rios Dunn"
},
{
"user_id": 11,
"name": "Walsh Robles"
},
{
"user_id": 12,
"name": "Nieves Ratliff"
},
{
"user_id": 13,
"name": "Alta Brennan"
},
{
"user_id": 14,
"name": "Theresa Gilliam"
}
]
},
{
"user_id": 13,
"name": "Cantu Griffin",
"children": [
{
"user_id": 0,
"name": "Gilmore Jordan"
},
{
"user_id": 1,
"name": "Mindy Mercado"
},
{
"user_id": 2,
"name": "Townsend Harmon"
},
{
"user_id": 3,
"name": "Bethany Mathis"
},
{
"user_id": 4,
"name": "Tonia Patel"
},
{
"user_id": 5,
"name": "Earnestine Foster"
},
{
"user_id": 6,
"name": "Wilson Evans"
},
{
"user_id": 7,
"name": "Olsen Wheeler"
},
{
"user_id": 8,
"name": "Mejia Hall"
},
{
"user_id": 9,
"name": "Viola Waller"
},
{
"user_id": 10,
"name": "Robbins Rivera"
},
{
"user_id": 11,
"name": "Lowe Yang"
},
{
"user_id": 12,
"name": "Riddle Cervantes"
},
{
"user_id": 13,
"name": "Rachel Soto"
},
{
"user_id": 14,
"name": "Gonzales Bond"
}
]
}
]
},
{
"user_id": 10,
"name": "Rosario Molina",
"children": [
{
"user_id": 0,
"name": "Robyn Garza",
"children": [
{
"user_id": 0,
"name": "Mable Hines"
},
{
"user_id": 1,
"name": "Angelica Mcdaniel"
},
{
"user_id": 2,
"name": "Raquel Cervantes"
},
{
"user_id": 3,
"name": "Nona Mcfadden"
},
{
"user_id": 4,
"name": "Pearl Mclaughlin"
},
{
"user_id": 5,
"name": "Bessie Ferguson"
},
{
"user_id": 6,
"name": "Gutierrez Collier"
},
{
"user_id": 7,
"name": "Rosanna Hopper"
},
{
"user_id": 8,
"name": "Eleanor Barlow"
},
{
"user_id": 9,
"name": "Krystal Wiley"
},
{
"user_id": 10,
"name": "Amalia Whitney"
},
{
"user_id": 11,
"name": "Hunt Dennis"
},
{
"user_id": 12,
"name": "Hobbs Doyle"
},
{
"user_id": 13,
"name": "Clarissa Bates"
},
{
"user_id": 14,
"name": "Ada Beck"
}
]
},
{
"user_id": 1,
"name": "Candace Gomez",
"children": [
{
"user_id": 0,
"name": "Bette Bolton"
},
{
"user_id": 1,
"name": "Mendoza Emerson"
},
{
"user_id": 2,
"name": "Natalie Powers"
},
{
"user_id": 3,
"name": "Bowen Massey"
},
{
"user_id": 4,
"name": "Lucia Hardy"
},
{
"user_id": 5,
"name": "Tillman Willis"
},
{
"user_id": 6,
"name": "Vinson Mcgowan"
},
{
"user_id": 7,
"name": "Leta Hoover"
},
{
"user_id": 8,
"name": "Barnett Gallegos"
},
{
"user_id": 9,
"name": "Keisha Bowen"
},
{
"user_id": 10,
"name": "Sharp Berger"
},
{
"user_id": 11,
"name": "Bates Davenport"
},
{
"user_id": 12,
"name": "Stuart Levy"
},
{
"user_id": 13,
"name": "Aurora Mercado"
},
{
"user_id": 14,
"name": "Callahan Sellers"
}
]
},
{
"user_id": 2,
"name": "Sharlene Mueller",
"children": [
{
"user_id": 0,
"name": "Selena Mooney"
},
{
"user_id": 1,
"name": "Iva Woodard"
},
{
"user_id": 2,
"name": "Olga Zimmerman"
},
{
"user_id": 3,
"name": "Christi Townsend"
},
{
"user_id": 4,
"name": "Augusta Rollins"
},
{
"user_id": 5,
"name": "Powell Bass"
},
{
"user_id": 6,
"name": "Morton Myers"
},
{
"user_id": 7,
"name": "Thompson Lowery"
},
{
"user_id": 8,
"name": "Sharon Soto"
},
{
"user_id": 9,
"name": "Maddox Potts"
},
{
"user_id": 10,
"name": "Heath Mayo"
},
{
"user_id": 11,
"name": "Oneal Bridges"
},
{
"user_id": 12,
"name": "Irene Conley"
},
{
"user_id": 13,
"name": "House Montoya"
},
{
"user_id": 14,
"name": "Jo Deleon"
}
]
},
{
"user_id": 3,
"name": "Erica Grimes",
"children": [
{
"user_id": 0,
"name": "Gloria Chapman"
},
{
"user_id": 1,
"name": "Vasquez Snyder"
},
{
"user_id": 2,
"name": "Ofelia Mclean"
},
{
"user_id": 3,
"name": "Jimenez Harvey"
},
{
"user_id": 4,
"name": "Jocelyn Joyner"
},
{
"user_id": 5,
"name": "Desiree Shaffer"
},
{
"user_id": 6,
"name": "Jana Delgado"
},
{
"user_id": 7,
"name": "Potter Mendez"
},
{
"user_id": 8,
"name": "Mallory Atkinson"
},
{
"user_id": 9,
"name": "Sabrina Tanner"
},
{
"user_id": 10,
"name": "Guerrero Mccall"
},
{
"user_id": 11,
"name": "Collier Trujillo"
},
{
"user_id": 12,
"name": "Pope Rivers"
},
{
"user_id": 13,
"name": "Jackson Ellison"
},
{
"user_id": 14,
"name": "Mcintosh Sosa"
}
]
},
{
"user_id": 4,
"name": "Wolfe Glenn",
"children": [
{
"user_id": 0,
"name": "Santana Johns"
},
{
"user_id": 1,
"name": "Rosemarie Castro"
},
{
"user_id": 2,
"name": "Mason Hanson"
},
{
"user_id": 3,
"name": "Luann Carter"
},
{
"user_id": 4,
"name": "Cherry George"
},
{
"user_id": 5,
"name": "Kirsten Munoz"
},
{
"user_id": 6,
"name": "Jacquelyn Stevens"
},
{
"user_id": 7,
"name": "Pat Witt"
},
{
"user_id": 8,
"name": "Romero Dixon"
},
{
"user_id": 9,
"name": "Washington Hurst"
},
{
"user_id": 10,
"name": "Mueller Sharpe"
},
{
"user_id": 11,
"name": "Avis Mccarthy"
},
{
"user_id": 12,
"name": "Erma Slater"
},
{
"user_id": 13,
"name": "Imogene Pearson"
},
{
"user_id": 14,
"name": "Marquez Contreras"
}
]
},
{
"user_id": 5,
"name": "Bond Hampton",
"children": [
{
"user_id": 0,
"name": "Jenny Bowers"
},
{
"user_id": 1,
"name": "Meadows Pope"
},
{
"user_id": 2,
"name": "Beck Cruz"
},
{
"user_id": 3,
"name": "Barbara Mcmahon"
},
{
"user_id": 4,
"name": "Ashley Morales"
},
{
"user_id": 5,
"name": "Ernestine Hinton"
},
{
"user_id": 6,
"name": "Hawkins Castillo"
},
{
"user_id": 7,
"name": "Carey Rowe"
},
{
"user_id": 8,
"name": "Whitaker Norman"
},
{
"user_id": 9,
"name": "Inez Ellis"
},
{
"user_id": 10,
"name": "Shauna Bryan"
},
{
"user_id": 11,
"name": "White Lawson"
},
{
"user_id": 12,
"name": "Lynnette Ware"
},
{
"user_id": 13,
"name": "Clements Barton"
},
{
"user_id": 14,
"name": "Armstrong Moon"
}
]
},
{
"user_id": 6,
"name": "Marguerite Hensley",
"children": [
{
"user_id": 0,
"name": "Wise Knowles"
},
{
"user_id": 1,
"name": "Kristy Jordan"
},
{
"user_id": 2,
"name": "Hodge Wilder"
},
{
"user_id": 3,
"name": "Jewel Fuller"
},
{
"user_id": 4,
"name": "Horne Luna"
},
{
"user_id": 5,
"name": "Mamie Acevedo"
},
{
"user_id": 6,
"name": "Drake Holder"
},
{
"user_id": 7,
"name": "Silva Yang"
},
{
"user_id": 8,
"name": "Wiggins Rodgers"
},
{
"user_id": 9,
"name": "Tamara Cohen"
},
{
"user_id": 10,
"name": "Leslie Mayer"
},
{
"user_id": 11,
"name": "Georgia Daniels"
},
{
"user_id": 12,
"name": "Julie Hansen"
},
{
"user_id": 13,
"name": "Gail Mullen"
},
{
"user_id": 14,
"name": "Diane Cummings"
}
]
},
{
"user_id": 7,
"name": "Myrtle Bartlett",
"children": [
{
"user_id": 0,
"name": "Jones Harrison"
},
{
"user_id": 1,
"name": "Carlson Pugh"
},
{
"user_id": 2,
"name": "Browning Shaw"
},
{
"user_id": 3,
"name": "Rosario Lamb"
},
{
"user_id": 4,
"name": "Ramos Evans"
},
{
"user_id": 5,
"name": "Rosalyn Rowland"
},
{
"user_id": 6,
"name": "Kerr Gilliam"
},
{
"user_id": 7,
"name": "Madden Kline"
},
{
"user_id": 8,
"name": "Todd West"
},
{
"user_id": 9,
"name": "Gwen Foster"
},
{
"user_id": 10,
"name": "Maude Melendez"
},
{
"user_id": 11,
"name": "Hanson Jacobs"
},
{
"user_id": 12,
"name": "Foreman Parsons"
},
{
"user_id": 13,
"name": "Ericka Holden"
},
{
"user_id": 14,
"name": "Mckay Keller"
}
]
},
{
"user_id": 8,
"name": "Imelda Oliver",
"children": [
{
"user_id": 0,
"name": "Alana Levine"
},
{
"user_id": 1,
"name": "Navarro Hernandez"
},
{
"user_id": 2,
"name": "Kim Torres"
},
{
"user_id": 3,
"name": "Virgie Hawkins"
},
{
"user_id": 4,
"name": "Angela Vang"
},
{
"user_id": 5,
"name": "Kellie Yates"
},
{
"user_id": 6,
"name": "Lenora Rodriguez"
},
{
"user_id": 7,
"name": "Cameron Burch"
},
{
"user_id": 8,
"name": "Chris Huffman"
},
{
"user_id": 9,
"name": "Reyna Gillespie"
},
{
"user_id": 10,
"name": "Sheila Richardson"
},
{
"user_id": 11,
"name": "Sutton Maddox"
},
{
"user_id": 12,
"name": "Salas Cross"
},
{
"user_id": 13,
"name": "Miranda Clarke"
},
{
"user_id": 14,
"name": "Sheppard Wynn"
}
]
},
{
"user_id": 9,
"name": "Martinez Walsh",
"children": [
{
"user_id": 0,
"name": "Bettye Romero"
},
{
"user_id": 1,
"name": "Michelle Avery"
},
{
"user_id": 2,
"name": "Oneil Pacheco"
},
{
"user_id": 3,
"name": "Hicks Sloan"
},
{
"user_id": 4,
"name": "Caldwell Woodward"
},
{
"user_id": 5,
"name": "Booker Finch"
},
{
"user_id": 6,
"name": "Shawna Mckee"
},
{
"user_id": 7,
"name": "Delia Olson"
},
{
"user_id": 8,
"name": "Nina Crawford"
},
{
"user_id": 9,
"name": "Marcie Whitley"
},
{
"user_id": 10,
"name": "Lewis Morin"
},
{
"user_id": 11,
"name": "Liz Parrish"
},
{
"user_id": 12,
"name": "Adrian Lynch"
},
{
"user_id": 13,
"name": "Massey Nash"
},
{
"user_id": 14,
"name": "Victoria Vance"
}
]
},
{
"user_id": 10,
"name": "Rosella Ramsey",
"children": [
{
"user_id": 0,
"name": "Hillary Hyde"
},
{
"user_id": 1,
"name": "Flossie Gentry"
},
{
"user_id": 2,
"name": "Atkins Huber"
},
{
"user_id": 3,
"name": "Lowe Brennan"
},
{
"user_id": 4,
"name": "Hale Melton"
},
{
"user_id": 5,
"name": "Betty Ball"
},
{
"user_id": 6,
"name": "Compton Nixon"
},
{
"user_id": 7,
"name": "Jacobs Sanchez"
},
{
"user_id": 8,
"name": "Campbell Cochran"
},
{
"user_id": 9,
"name": "Dorsey Hubbard"
},
{
"user_id": 10,
"name": "Ramona Tucker"
},
{
"user_id": 11,
"name": "Weaver Jacobson"
},
{
"user_id": 12,
"name": "Wade Cantu"
},
{
"user_id": 13,
"name": "Harvey Collins"
},
{
"user_id": 14,
"name": "Marisa Harmon"
}
]
},
{
"user_id": 11,
"name": "Randolph Humphrey",
"children": [
{
"user_id": 0,
"name": "Dora Warner"
},
{
"user_id": 1,
"name": "Adriana Richmond"
},
{
"user_id": 2,
"name": "Lelia Macdonald"
},
{
"user_id": 3,
"name": "Elma Bean"
},
{
"user_id": 4,
"name": "Richards Park"
},
{
"user_id": 5,
"name": "Lara Weber"
},
{
"user_id": 6,
"name": "Puckett Delacruz"
},
{
"user_id": 7,
"name": "Lakisha Day"
},
{
"user_id": 8,
"name": "Goodman Palmer"
},
{
"user_id": 9,
"name": "Lina Newton"
},
{
"user_id": 10,
"name": "Jeannette Oneill"
},
{
"user_id": 11,
"name": "Ray Sears"
},
{
"user_id": 12,
"name": "Mooney Pierce"
},
{
"user_id": 13,
"name": "Clay Randolph"
},
{
"user_id": 14,
"name": "Denise Savage"
}
]
},
{
"user_id": 12,
"name": "Carey Arnold",
"children": [
{
"user_id": 0,
"name": "Cooper Scott"
},
{
"user_id": 1,
"name": "Edwina Rosario"
},
{
"user_id": 2,
"name": "Cassie Butler"
},
{
"user_id": 3,
"name": "Hogan Buckley"
},
{
"user_id": 4,
"name": "Betsy Reed"
},
{
"user_id": 5,
"name": "Beasley Schneider"
},
{
"user_id": 6,
"name": "Luella Walker"
},
{
"user_id": 7,
"name": "Woodard Avila"
},
{
"user_id": 8,
"name": "Dominique Wise"
},
{
"user_id": 9,
"name": "Wendi Burns"
},
{
"user_id": 10,
"name": "Dana Copeland"
},
{
"user_id": 11,
"name": "Martina Hickman"
},
{
"user_id": 12,
"name": "Mcclain Powell"
},
{
"user_id": 13,
"name": "Woods Hahn"
},
{
"user_id": 14,
"name": "Sloan Reid"
}
]
},
{
"user_id": 13,
"name": "Latasha Waller",
"children": [
{
"user_id": 0,
"name": "Parks Murray"
},
{
"user_id": 1,
"name": "Rowena Taylor"
},
{
"user_id": 2,
"name": "Alford Vincent"
},
{
"user_id": 3,
"name": "Gena Cote"
},
{
"user_id": 4,
"name": "Wilkins Solomon"
},
{
"user_id": 5,
"name": "Gallagher Barnett"
},
{
"user_id": 6,
"name": "Darla Spencer"
},
{
"user_id": 7,
"name": "Stokes Calhoun"
},
{
"user_id": 8,
"name": "Wallace Moore"
},
{
"user_id": 9,
"name": "Barnes White"
},
{
"user_id": 10,
"name": "Bridges English"
},
{
"user_id": 11,
"name": "Lindsey Hester"
},
{
"user_id": 12,
"name": "Marsh Guerrero"
},
{
"user_id": 13,
"name": "Williamson Noble"
},
{
"user_id": 14,
"name": "Lavonne Nelson"
}
]
},
{
"user_id": 14,
"name": "Blanca Holmes",
"children": [
{
"user_id": 0,
"name": "Cynthia Tran"
},
{
"user_id": 1,
"name": "Tamra Carver"
},
{
"user_id": 2,
"name": "Oconnor Acosta"
},
{
"user_id": 3,
"name": "Maxine Ratliff"
},
{
"user_id": 4,
"name": "Lindsay Cannon"
},
{
"user_id": 5,
"name": "Carney Harrington"
},
{
"user_id": 6,
"name": "Millie Roach"
},
{
"user_id": 7,
"name": "Waters Odom"
},
{
"user_id": 8,
"name": "Heidi Gill"
},
{
"user_id": 9,
"name": "Gracie Guzman"
},
{
"user_id": 10,
"name": "Grant Mack"
},
{
"user_id": 11,
"name": "Rosalinda Webb"
},
{
"user_id": 12,
"name": "Jarvis Whitfield"
},
{
"user_id": 13,
"name": "Veronica Stein"
},
{
"user_id": 14,
"name": "Harmon Kidd"
}
]
}
]
}
]
},
{
"user_id": 1,
"name": "Constance Prince",
"children": [
{
"user_id": 1,
"name": "Faith Phelps",
"children": [
{
"user_id": 0,
"name": "Mcgowan Fernandez",
"children": [
{
"user_id": 0,
"name": "Rollins Joyce"
},
{
"user_id": 1,
"name": "Shawna Ortiz"
},
{
"user_id": 2,
"name": "Dorothy Frank"
},
{
"user_id": 3,
"name": "Wyatt Hays"
},
{
"user_id": 4,
"name": "Barrett Haney"
},
{
"user_id": 5,
"name": "Francesca Kinney"
},
{
"user_id": 6,
"name": "Brady Cohen"
},
{
"user_id": 7,
"name": "Tanner Lloyd"
},
{
"user_id": 8,
"name": "Adkins Page"
},
{
"user_id": 9,
"name": "Janette Anthony"
},
{
"user_id": 10,
"name": "Alberta Solomon"
},
{
"user_id": 11,
"name": "Stout Santana"
},
{
"user_id": 12,
"name": "Stuart Decker"
},
{
"user_id": 13,
"name": "Oconnor Wallace"
},
{
"user_id": 14,
"name": "Wendy Farrell"
}
]
},
{
"user_id": 1,
"name": "Pickett Sherman",
"children": [
{
"user_id": 0,
"name": "Vang Salinas"
},
{
"user_id": 1,
"name": "Alvarado Sanchez"
},
{
"user_id": 2,
"name": "Hanson Giles"
},
{
"user_id": 3,
"name": "Eloise Miranda"
},
{
"user_id": 4,
"name": "May Douglas"
},
{
"user_id": 5,
"name": "Johanna Ellis"
},
{
"user_id": 6,
"name": "Irma Chang"
},
{
"user_id": 7,
"name": "Violet Horn"
},
{
"user_id": 8,
"name": "Christi Townsend"
},
{
"user_id": 9,
"name": "Jerry Patrick"
},
{
"user_id": 10,
"name": "Morrison Morales"
},
{
"user_id": 11,
"name": "Terrell Schneider"
},
{
"user_id": 12,
"name": "Katherine Blair"
},
{
"user_id": 13,
"name": "Walters Dean"
},
{
"user_id": 14,
"name": "Penelope Hinton"
}
]
},
{
"user_id": 2,
"name": "Jerri Evans",
"children": [
{
"user_id": 0,
"name": "Dawson Levine"
},
{
"user_id": 1,
"name": "Tracie Levy"
},
{
"user_id": 2,
"name": "Walton Kidd"
},
{
"user_id": 3,
"name": "Mueller Sykes"
},
{
"user_id": 4,
"name": "Knapp Hunt"
},
{
"user_id": 5,
"name": "Hoover Rojas"
},
{
"user_id": 6,
"name": "Iva Hernandez"
},
{
"user_id": 7,
"name": "Irene Blankenship"
},
{
"user_id": 8,
"name": "Sosa Ochoa"
},
{
"user_id": 9,
"name": "Knight Black"
},
{
"user_id": 10,
"name": "Olivia Peters"
},
{
"user_id": 11,
"name": "Fernandez Fletcher"
},
{
"user_id": 12,
"name": "Jamie Underwood"
},
{
"user_id": 13,
"name": "Montoya Hartman"
},
{
"user_id": 14,
"name": "Rosemary Castro"
}
]
},
{
"user_id": 3,
"name": "Hurley Dunn",
"children": [
{
"user_id": 0,
"name": "Rodgers Ellison"
},
{
"user_id": 1,
"name": "Richard Whitney"
},
{
"user_id": 2,
"name": "Haley Boyle"
},
{
"user_id": 3,
"name": "Jefferson Brown"
},
{
"user_id": 4,
"name": "Stacey Brock"
},
{
"user_id": 5,
"name": "Melba House"
},
{
"user_id": 6,
"name": "Charles Frost"
},
{
"user_id": 7,
"name": "Schmidt Holcomb"
},
{
"user_id": 8,
"name": "Liz Martinez"
},
{
"user_id": 9,
"name": "Summers Estrada"
},
{
"user_id": 10,
"name": "Pittman Lawson"
},
{
"user_id": 11,
"name": "Whitfield Dennis"
},
{
"user_id": 12,
"name": "Travis Chapman"
},
{
"user_id": 13,
"name": "Amy Hester"
},
{
"user_id": 14,
"name": "Willie Davidson"
}
]
},
{
"user_id": 4,
"name": "Shelia Rogers",
"children": [
{
"user_id": 0,
"name": "Knox Ferguson"
},
{
"user_id": 1,
"name": "Hansen Carey"
},
{
"user_id": 2,
"name": "Misty Weber"
},
{
"user_id": 3,
"name": "Diane Peterson"
},
{
"user_id": 4,
"name": "Gracie Yang"
},
{
"user_id": 5,
"name": "Campos Bradford"
},
{
"user_id": 6,
"name": "Jo Cabrera"
},
{
"user_id": 7,
"name": "Angie Compton"
},
{
"user_id": 8,
"name": "Chase Miles"
},
{
"user_id": 9,
"name": "Donaldson Pittman"
},
{
"user_id": 10,
"name": "Reba Vance"
},
{
"user_id": 11,
"name": "Dominique Blackwell"
},
{
"user_id": 12,
"name": "Mildred Tillman"
},
{
"user_id": 13,
"name": "Obrien Fields"
},
{
"user_id": 14,
"name": "Margret Hebert"
}
]
},
{
"user_id": 5,
"name": "Mann Nolan",
"children": [
{
"user_id": 0,
"name": "Earline Ayers"
},
{
"user_id": 1,
"name": "Eddie Davenport"
},
{
"user_id": 2,
"name": "Alana Mann"
},
{
"user_id": 3,
"name": "Rosanna Norris"
},
{
"user_id": 4,
"name": "Fisher Gray"
},
{
"user_id": 5,
"name": "Rowland Velazquez"
},
{
"user_id": 6,
"name": "Nanette Dawson"
},
{
"user_id": 7,
"name": "Maureen Murray"
},
{
"user_id": 8,
"name": "Ashley Joseph"
},
{
"user_id": 9,
"name": "Bonner Mercado"
},
{
"user_id": 10,
"name": "Elise Woodward"
},
{
"user_id": 11,
"name": "Bianca Colon"
},
{
"user_id": 12,
"name": "Johnson Gilbert"
},
{
"user_id": 13,
"name": "Dixon Neal"
},
{
"user_id": 14,
"name": "Karen Thornton"
}
]
},
{
"user_id": 6,
"name": "Vaughn Guthrie",
"children": [
{
"user_id": 0,
"name": "Henrietta Norman"
},
{
"user_id": 1,
"name": "Maldonado Peck"
},
{
"user_id": 2,
"name": "Pitts Snider"
},
{
"user_id": 3,
"name": "Ingrid Simpson"
},
{
"user_id": 4,
"name": "Bridgett Pena"
},
{
"user_id": 5,
"name": "Adams Davis"
},
{
"user_id": 6,
"name": "Larson Petersen"
},
{
"user_id": 7,
"name": "Goldie Strong"
},
{
"user_id": 8,
"name": "Sandy Hood"
},
{
"user_id": 9,
"name": "Garrison Knapp"
},
{
"user_id": 10,
"name": "Leann Hickman"
},
{
"user_id": 11,
"name": "Franco Fischer"
},
{
"user_id": 12,
"name": "Tabitha Sawyer"
},
{
"user_id": 13,
"name": "Porter Willis"
},
{
"user_id": 14,
"name": "Chan Floyd"
}
]
},
{
"user_id": 7,
"name": "Wood Schroeder",
"children": [
{
"user_id": 0,
"name": "Yesenia Rice"
},
{
"user_id": 1,
"name": "Sharon Vaughn"
},
{
"user_id": 2,
"name": "Ward Fuentes"
},
{
"user_id": 3,
"name": "Reese Adkins"
},
{
"user_id": 4,
"name": "Henderson Brooks"
},
{
"user_id": 5,
"name": "Davidson Pope"
},
{
"user_id": 6,
"name": "Toni Richardson"
},
{
"user_id": 7,
"name": "Colleen Atkins"
},
{
"user_id": 8,
"name": "Webster Gilliam"
},
{
"user_id": 9,
"name": "Muriel Goodman"
},
{
"user_id": 10,
"name": "Hooper Daniels"
},
{
"user_id": 11,
"name": "Farrell Rivera"
},
{
"user_id": 12,
"name": "Rae Wiley"
},
{
"user_id": 13,
"name": "Abigail Williamson"
},
{
"user_id": 14,
"name": "Kline Benton"
}
]
},
{
"user_id": 8,
"name": "Joan Ryan",
"children": [
{
"user_id": 0,
"name": "Kelley Carney"
},
{
"user_id": 1,
"name": "Tiffany Nicholson"
},
{
"user_id": 2,
"name": "Brennan Casey"
},
{
"user_id": 3,
"name": "Neal Osborn"
},
{
"user_id": 4,
"name": "Miranda Dodson"
},
{
"user_id": 5,
"name": "Thompson Mcfarland"
},
{
"user_id": 6,
"name": "Fleming Rutledge"
},
{
"user_id": 7,
"name": "Bernadette Jacobson"
},
{
"user_id": 8,
"name": "Petra Hicks"
},
{
"user_id": 9,
"name": "Marquez Michael"
},
{
"user_id": 10,
"name": "Donovan Bryan"
},
{
"user_id": 11,
"name": "Hope Morton"
},
{
"user_id": 12,
"name": "Elvira Cotton"
},
{
"user_id": 13,
"name": "Frankie Tran"
},
{
"user_id": 14,
"name": "Guy Griffith"
}
]
},
{
"user_id": 9,
"name": "Talley Simmons",
"children": [
{
"user_id": 0,
"name": "Bass Mcdowell"
},
{
"user_id": 1,
"name": "Ofelia Montoya"
},
{
"user_id": 2,
"name": "Agnes Nelson"
},
{
"user_id": 3,
"name": "Tamera Hill"
},
{
"user_id": 4,
"name": "Miranda Ruiz"
},
{
"user_id": 5,
"name": "Mcdaniel Barnett"
},
{
"user_id": 6,
"name": "Rich Bean"
},
{
"user_id": 7,
"name": "Hines Griffin"
},
{
"user_id": 8,
"name": "Erna Farley"
},
{
"user_id": 9,
"name": "Burgess Scott"
},
{
"user_id": 10,
"name": "Chris Howe"
},
{
"user_id": 11,
"name": "Tammie Cline"
},
{
"user_id": 12,
"name": "Booth Sexton"
},
{
"user_id": 13,
"name": "Harper Durham"
},
{
"user_id": 14,
"name": "Dollie May"
}
]
},
{
"user_id": 10,
"name": "Alicia Glass",
"children": [
{
"user_id": 0,
"name": "Cheryl Conrad"
},
{
"user_id": 1,
"name": "Patti Miller"
},
{
"user_id": 2,
"name": "Neva Mcgowan"
},
{
"user_id": 3,
"name": "Hutchinson Whitehead"
},
{
"user_id": 4,
"name": "Kate Vaughn"
},
{
"user_id": 5,
"name": "Hogan Barrett"
},
{
"user_id": 6,
"name": "Tami Conway"
},
{
"user_id": 7,
"name": "Michael Velez"
},
{
"user_id": 8,
"name": "Cornelia Brewer"
},
{
"user_id": 9,
"name": "Thompson Watkins"
},
{
"user_id": 10,
"name": "Morrow Cabrera"
},
{
"user_id": 11,
"name": "Rose Berg"
},
{
"user_id": 12,
"name": "Case Kerr"
},
{
"user_id": 13,
"name": "Imelda Rivas"
},
{
"user_id": 14,
"name": "Frances Wyatt"
}
]
},
{
"user_id": 11,
"name": "Weaver Beck",
"children": [
{
"user_id": 0,
"name": "Kimberly Osborne"
},
{
"user_id": 1,
"name": "Hannah Carey"
},
{
"user_id": 2,
"name": "Emily Mcintyre"
},
{
"user_id": 3,
"name": "Melba Horn"
},
{
"user_id": 4,
"name": "Serena Perez"
},
{
"user_id": 5,
"name": "Johnnie Holder"
},
{
"user_id": 6,
"name": "Wiggins Greer"
},
{
"user_id": 7,
"name": "Weiss Peters"
},
{
"user_id": 8,
"name": "Barrett Rutledge"
},
{
"user_id": 9,
"name": "Burris Hebert"
},
{
"user_id": 10,
"name": "Chrystal Vasquez"
},
{
"user_id": 11,
"name": "Zamora Rodriquez"
},
{
"user_id": 12,
"name": "Laurie Benjamin"
},
{
"user_id": 13,
"name": "Alice Rodgers"
},
{
"user_id": 14,
"name": "Susie Blankenship"
}
]
},
{
"user_id": 12,
"name": "Lindsay Cohen",
"children": [
{
"user_id": 0,
"name": "Sanders Shaw"
},
{
"user_id": 1,
"name": "Clay Madden"
},
{
"user_id": 2,
"name": "Sheena Merrill"
},
{
"user_id": 3,
"name": "Kris Graham"
},
{
"user_id": 4,
"name": "Adrian Morales"
},
{
"user_id": 5,
"name": "Vickie Everett"
},
{
"user_id": 6,
"name": "Abbott Calhoun"
},
{
"user_id": 7,
"name": "Hayes Leonard"
},
{
"user_id": 8,
"name": "Gould Brock"
},
{
"user_id": 9,
"name": "Vinson Fowler"
},
{
"user_id": 10,
"name": "Chambers Howell"
},
{
"user_id": 11,
"name": "Darla Bradshaw"
},
{
"user_id": 12,
"name": "Nancy Marshall"
},
{
"user_id": 13,
"name": "Leann Harper"
},
{
"user_id": 14,
"name": "Cindy Wilcox"
}
]
},
{
"user_id": 13,
"name": "Glenda Dickerson",
"children": [
{
"user_id": 0,
"name": "Melanie Reyes"
},
{
"user_id": 1,
"name": "Ada Rhodes"
},
{
"user_id": 2,
"name": "Ursula Santos"
},
{
"user_id": 3,
"name": "Lesley Gibson"
},
{
"user_id": 4,
"name": "Frazier Gillespie"
},
{
"user_id": 5,
"name": "Rosanne Clayton"
},
{
"user_id": 6,
"name": "Noemi Carver"
},
{
"user_id": 7,
"name": "Young Massey"
},
{
"user_id": 8,
"name": "King Hutchinson"
},
{
"user_id": 9,
"name": "Sharron Patterson"
},
{
"user_id": 10,
"name": "Browning Gates"
},
{
"user_id": 11,
"name": "Renee Vance"
},
{
"user_id": 12,
"name": "Kristina Wheeler"
},
{
"user_id": 13,
"name": "Bowers Macdonald"
},
{
"user_id": 14,
"name": "Russo Cross"
}
]
},
{
"user_id": 14,
"name": "Sykes Rosa",
"children": [
{
"user_id": 0,
"name": "Sellers Ingram"
},
{
"user_id": 1,
"name": "Marietta Shelton"
},
{
"user_id": 2,
"name": "Cummings Carroll"
},
{
"user_id": 3,
"name": "Lucas Reilly"
},
{
"user_id": 4,
"name": "Jane Hester"
},
{
"user_id": 5,
"name": "Amanda Walsh"
},
{
"user_id": 6,
"name": "Christian Sanchez"
},
{
"user_id": 7,
"name": "Audrey Alexander"
},
{
"user_id": 8,
"name": "Emma Park"
},
{
"user_id": 9,
"name": "Angelita Vang"
},
{
"user_id": 10,
"name": "Shawna Bray"
},
{
"user_id": 11,
"name": "Herring Pena"
},
{
"user_id": 12,
"name": "Wilma Dixon"
},
{
"user_id": 13,
"name": "Jerri Kemp"
},
{
"user_id": 14,
"name": "Rush Price"
}
]
}
]
},
{
"user_id": 2,
"name": "Young Levine",
"children": [
{
"user_id": 5,
"name": "Chaney Bell",
"children": [
{
"user_id": 0,
"name": "Elma Bass"
},
{
"user_id": 1,
"name": "Marylou Guy"
},
{
"user_id": 2,
"name": "Brooke Baird"
},
{
"user_id": 3,
"name": "Kathryn Stout"
},
{
"user_id": 4,
"name": "Holman Pugh"
},
{
"user_id": 5,
"name": "Lawson Blackwell"
},
{
"user_id": 6,
"name": "Lily Strong"
},
{
"user_id": 7,
"name": "Sharon Duffy"
},
{
"user_id": 8,
"name": "Bennett Cook"
},
{
"user_id": 9,
"name": "Ines Conley"
},
{
"user_id": 10,
"name": "Ross Reid"
},
{
"user_id": 11,
"name": "Leach Pratt"
},
{
"user_id": 12,
"name": "Lilly Cole"
},
{
"user_id": 13,
"name": "Schultz Hart"
},
{
"user_id": 14,
"name": "Gilbert Gilbert"
}
]
},
{
"user_id": 11,
"name": "Carey Odonnell",
"children": [
{
"user_id": 0,
"name": "Robinson Vazquez"
},
{
"user_id": 1,
"name": "Mandy Wise"
},
{
"user_id": 2,
"name": "Mcclain Sanford"
},
{
"user_id": 3,
"name": "Taylor Wooten"
},
{
"user_id": 4,
"name": "Weber Best"
},
{
"user_id": 5,
"name": "Cecelia Henson"
},
{
"user_id": 6,
"name": "Rhonda Baker"
},
{
"user_id": 7,
"name": "Cara Gregory"
},
{
"user_id": 8,
"name": "James Walter"
},
{
"user_id": 9,
"name": "Christa Roth"
},
{
"user_id": 10,
"name": "Stevenson Rodriguez"
},
{
"user_id": 11,
"name": "Johanna Cummings"
},
{
"user_id": 12,
"name": "Vanessa Collins"
},
{
"user_id": 13,
"name": "Davidson Meyer"
},
{
"user_id": 14,
"name": "Peggy King"
}
]
},
{
"user_id": 13,
"name": "Anna Forbes",
"children": [
{
"user_id": 0,
"name": "Jeanne Romero"
},
{
"user_id": 1,
"name": "Kelley Keller"
},
{
"user_id": 2,
"name": "Kaitlin Mathis"
},
{
"user_id": 3,
"name": "Gordon Keith"
},
{
"user_id": 4,
"name": "Mavis Parker"
},
{
"user_id": 5,
"name": "Dejesus Walls"
},
{
"user_id": 6,
"name": "Ratliff Shaffer"
},
{
"user_id": 7,
"name": "Maryellen Gomez"
},
{
"user_id": 8,
"name": "Hudson Christian"
},
{
"user_id": 9,
"name": "Natalia Bond"
},
{
"user_id": 10,
"name": "Newton Pitts"
},
{
"user_id": 11,
"name": "Matilda Rivera"
},
{
"user_id": 12,
"name": "Palmer Pickett"
},
{
"user_id": 13,
"name": "Bradley Mckinney"
},
{
"user_id": 14,
"name": "Shelia Galloway"
}
]
}
]
}
]
}
]
};
// Get JSON data
//treeJSON = d3.json('hey', function(error, treeData) {
// Calculate total nodes, max label length
var totalNodes = 0;
var maxLabelLength = 0;
// variables for drag/drop
var selectedNode = null;
var draggingNode = null;
// panning variables
var panSpeed = 200;
var panBoundary = 20; // Within 20px from edges will pan when dragging.
// Misc. variables
var i = 0;
var duration = 750;
var root;
// size of the diagram
var viewerWidth = $(document).width();
var viewerHeight = $(document).height();
var tree = d3.layout.tree()
.size([viewerHeight, viewerWidth]);
// define a d3 diagonal projection for use by the node paths later on.
var diagonal = d3.svg.diagonal()
.projection(function(d) {
return [d.y, d.x];
});
// A recursive helper function for performing some setup by walking through all nodes
function visit(parent, visitFn, childrenFn) {
if (!parent) return;
visitFn(parent);
var children = childrenFn(parent);
if (children) {
var count = children.length;
for (var i = 0; i < count; i++) {
visit(children[i], visitFn, childrenFn);
}
}
}
// Call visit function to establish maxLabelLength
visit(treeData, function(d) {
totalNodes++;
console.log(d);
maxLabelLength = 10;
console.log("after");
}, function(d) {
return d.children && d.children.length > 0 ? d.children : null;
});
// sort the tree according to the node names
function sortTree() {
tree.sort(function(a, b) {
if (b.name !== undefined && a.name !== undefined) {
return b.name.toLowerCase() < a.name.toLowerCase() ? 1 : -1;
} else {
return 100000;
}
});
}
// Sort the tree initially incase the JSON isn't in a sorted order.
sortTree();
// TODO: Pan function, can be better implemented.
function pan(domNode, direction) {
var speed = panSpeed;
if (panTimer) {
clearTimeout(panTimer);
translateCoords = d3.transform(svgGroup.attr("transform"));
if (direction == 'left' || direction == 'right') {
translateX = direction == 'left' ? translateCoords.translate[0] + speed : translateCoords.translate[0] - speed;
translateY = translateCoords.translate[1];
} else if (direction == 'up' || direction == 'down') {
translateX = translateCoords.translate[0];
translateY = direction == 'up' ? translateCoords.translate[1] + speed : translateCoords.translate[1] - speed;
}
scaleX = translateCoords.scale[0];
scaleY = translateCoords.scale[1];
scale = zoomListener.scale();
svgGroup.transition().attr("transform", "translate(" + translateX + "," + translateY + ")scale(" + scale + ")");
d3.select(domNode).select('g.node').attr("transform", "translate(" + translateX + "," + translateY + ")");
zoomListener.scale(zoomListener.scale());
zoomListener.translate([translateX, translateY]);
panTimer = setTimeout(function() {
pan(domNode, speed, direction);
}, 50);
}
}
// Define the zoom function for the zoomable tree
function zoom() {
svgGroup.attr("transform", "translate(" + d3.event.translate + ")scale(" + d3.event.scale + ")");
}
// define the zoomListener which calls the zoom function on the "zoom" event constrained within the scaleExtents
var zoomListener = d3.behavior.zoom().scaleExtent([0.1, 3]).on("zoom", zoom);
function initiateDrag(d, domNode) {
draggingNode = d;
d3.select(domNode).select('.ghostCircle').attr('pointer-events', 'none');
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle show');
d3.select(domNode).attr('class', 'node activeDrag');
svgGroup.selectAll("g.node").sort(function(a, b) { // select the parent and sort the path's
if (a.id != draggingNode.id) return 1; // a is not the hovered element, send "a" to the back
else return -1; // a is the hovered element, bring "a" to the front
});
// if nodes has children, remove the links and nodes
if (nodes.length > 1) {
// remove link paths
links = tree.links(nodes);
nodePaths = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
}).remove();
// remove child nodes
nodesExit = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id;
}).filter(function(d, i) {
if (d.id == draggingNode.id) {
return false;
}
return true;
}).remove();
}
// remove parent link
parentLink = tree.links(tree.nodes(draggingNode.parent));
svgGroup.selectAll('path.link').filter(function(d, i) {
if (d.target.id == draggingNode.id) {
return true;
}
return false;
}).remove();
dragStarted = null;
}
// define the baseSvg, attaching a class for styling and the zoomListener
var baseSvg = d3.select("#tree-container").append("svg")
.attr("width", viewerWidth)
.attr("height", viewerHeight)
.attr("class", "overlay")
.call(zoomListener);
// Define the drag listeners for drag/drop behaviour of nodes.
dragListener = d3.behavior.drag()
.on("dragstart", function(d) {
if (d == root) {
return;
}
dragStarted = true;
nodes = tree.nodes(d);
d3.event.sourceEvent.stopPropagation();
// it's important that we suppress the mouseover event on the node being dragged. Otherwise it will absorb the mouseover event and the underlying node will not detect it d3.select(this).attr('pointer-events', 'none');
})
.on("drag", function(d) {
if (d == root) {
return;
}
if (dragStarted) {
domNode = this;
initiateDrag(d, domNode);
}
// get coords of mouseEvent relative to svg container to allow for panning
relCoords = d3.mouse($('svg').get(0));
if (relCoords[0] < panBoundary) {
panTimer = true;
pan(this, 'left');
} else if (relCoords[0] > ($('svg').width() - panBoundary)) {
panTimer = true;
pan(this, 'right');
} else if (relCoords[1] < panBoundary) {
panTimer = true;
pan(this, 'up');
} else if (relCoords[1] > ($('svg').height() - panBoundary)) {
panTimer = true;
pan(this, 'down');
} else {
try {
clearTimeout(panTimer);
} catch (e) {
}
}
d.x0 += d3.event.dy;
d.y0 += d3.event.dx;
var node = d3.select(this);
node.attr("transform", "translate(" + d.y0 + "," + d.x0 + ")");
updateTempConnector();
}).on("dragend", function(d) {
if (d == root) {
return;
}
domNode = this;
if (selectedNode) {
// now remove the element from the parent, and insert it into the new elements children
var index = draggingNode.parent.children.indexOf(draggingNode);
if (index > -1) {
draggingNode.parent.children.splice(index, 1);
}
if (typeof selectedNode.children !== 'undefined' || typeof selectedNode._children !== 'undefined') {
if (typeof selectedNode.children !== 'undefined') {
selectedNode.children.push(draggingNode);
} else {
selectedNode._children.push(draggingNode);
}
} else {
selectedNode.children = [];
selectedNode.children.push(draggingNode);
}
// Make sure that the node being added to is expanded so user can see added node is correctly moved
expand(selectedNode);
sortTree();
endDrag();
} else {
endDrag();
}
});
function endDrag() {
selectedNode = null;
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle');
d3.select(domNode).attr('class', 'node');
// now restore the mouseover event or we won't be able to drag a 2nd time
d3.select(domNode).select('.ghostCircle').attr('pointer-events', '');
updateTempConnector();
if (draggingNode !== null) {
update(root);
centerNode(draggingNode);
draggingNode = null;
}
}
// Helper functions for collapsing and expanding nodes.
function collapse(d) {
if (d.children) {
d._children = d.children;
d._children.forEach(collapse);
d.children = null;
}
}
function expand(d) {
if (d._children) {
d.children = d._children;
d.children.forEach(expand);
d._children = null;
}
}
var overCircle = function(d) {
selectedNode = d;
updateTempConnector();
};
var outCircle = function(d) {
selectedNode = null;
updateTempConnector();
};
// Function to update the temporary connector indicating dragging affiliation
var updateTempConnector = function() {
var data = [];
if (draggingNode !== null && selectedNode !== null) {
// have to flip the source coordinates since we did this for the existing connectors on the original tree
data = [{
source: {
x: selectedNode.y0,
y: selectedNode.x0
},
target: {
x: draggingNode.y0,
y: draggingNode.x0
}
}];
}
var link = svgGroup.selectAll(".templink").data(data);
link.enter().append("path")
.attr("class", "templink")
.attr("d", d3.svg.diagonal())
.attr('pointer-events', 'none');
link.attr("d", d3.svg.diagonal());
link.exit().remove();
};
// Function to center node when clicked/dropped so node doesn't get lost when collapsing/moving with large amount of children.
function centerNode(source) {
scale = zoomListener.scale();
x = -source.y0;
y = -source.x0;
x = x * scale + viewerWidth / 2;
y = y * scale + viewerHeight / 2;
d3.select('g').transition()
.duration(duration)
.attr("transform", "translate(" + x + "," + y + ")scale(" + scale + ")");
zoomListener.scale(scale);
zoomListener.translate([x, y]);
}
// Toggle children function
function toggleChildren(d) {
if (d.children) {
d._children = d.children;
d.children = null;
} else if (d._children) {
d.children = d._children;
d._children = null;
}
return d;
}
// Toggle children on click.
function click(d) {
if (d3.event.defaultPrevented) return; // click suppressed
d = toggleChildren(d);
update(d);
centerNode(d);
}
function update(source) {
// Compute the new height, function counts total children of root node and sets tree height accordingly.
// This prevents the layout looking squashed when new nodes are made visible or looking sparse when nodes are removed
// This makes the layout more consistent.
var levelWidth = [1];
var childCount = function(level, n) {
if (n.children && n.children.length > 0) {
if (levelWidth.length <= level + 1) levelWidth.push(0);
levelWidth[level + 1] += n.children.length;
n.children.forEach(function(d) {
childCount(level + 1, d);
});
}
};
childCount(0, root);
var newHeight = d3.max(levelWidth) * 25; // 25 pixels per line
tree = tree.size([newHeight, viewerWidth]);
// Compute the new tree layout.
var nodes = tree.nodes(root).reverse(),
links = tree.links(nodes);
// Set widths between levels based on maxLabelLength.
nodes.forEach(function(d) {
d.y = (d.depth * (maxLabelLength * 10)); //maxLabelLength * 10px
// alternatively to keep a fixed scale one can set a fixed depth per level
// Normalize for fixed-depth by commenting out below line
// d.y = (d.depth * 500); //500px per level.
});
// Update the nodes…
node = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id || (d.id = ++i);
});
// Enter any new nodes at the parent's previous position.
var nodeEnter = node.enter().append("g")
.call(dragListener)
.attr("class", "node")
.attr("transform", function(d) {
return "translate(" + source.y0 + "," + source.x0 + ")";
})
.on('click', click);
nodeEnter.append("circle")
.attr('class', 'nodeCircle')
.attr("r", 0)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
nodeEnter.append("text")
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("dy", ".35em")
.attr('class', 'nodeText')
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
})
.style("fill-opacity", 0);
// phantom node to give us mouseover in a radius around it
nodeEnter.append("circle")
.attr('class', 'ghostCircle')
.attr("r", 30)
.attr("opacity", 0.2) // change this to zero to hide the target area
.style("fill", "red")
.attr('pointer-events', 'mouseover')
.on("mouseover", function(node) {
overCircle(node);
})
.on("mouseout", function(node) {
outCircle(node);
});
// Update the text to reflect whether node has children or not.
node.select('text')
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
});
// Change the circle fill depending on whether it has children and is collapsed
node.select("circle.nodeCircle")
.attr("r", 4.5)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
// Transition nodes to their new position.
var nodeUpdate = node.transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + d.y + "," + d.x + ")";
});
// Fade the text in
nodeUpdate.select("text")
.style("fill-opacity", 1);
// Transition exiting nodes to the parent's new position.
var nodeExit = node.exit().transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + source.y + "," + source.x + ")";
})
.remove();
nodeExit.select("circle")
.attr("r", 0);
nodeExit.select("text")
.style("fill-opacity", 0);
// Update the links…
var link = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
});
// Enter any new links at the parent's previous position.
link.enter().insert("path", "g")
.attr("class", "link")
.attr("d", function(d) {
var o = {
x: source.x0,
y: source.y0
};
return diagonal({
source: o,
target: o
});
});
// Transition links to their new position.
link.transition()
.duration(duration)
.attr("d", diagonal);
// Transition exiting nodes to the parent's new position.
link.exit().transition()
.duration(duration)
.attr("d", function(d) {
var o = {
x: source.x,
y: source.y
};
return diagonal({
source: o,
target: o
});
})
.remove();
// Stash the old positions for transition.
nodes.forEach(function(d) {
d.x0 = d.x;
d.y0 = d.y;
});
}
// Append a group which holds all nodes and which the zoom Listener can act upon.
var svgGroup = baseSvg.append("g");
// Define the root
root = treeData;
root.x0 = viewerHeight / 2;
root.y0 = 0;
// Collapse all children of roots children before rendering.
root.children.forEach(function(child){
collapse(child);
});
// Layout the tree initially and center on the root node.
update(root);
centerNode(root);
//});
</script></body>
</html>
var treeData = {
"user_id": 0,
"name": "Root Node",
"children": [
{
"user_id": 0,
"name": "Flossie Hickman",
"children": [
{
"user_id": 0,
"name": "Violet Arnold",
"children": [
{
"user_id": 4,
"name": "Sabrina Harrell",
"children": [
{
"user_id": 0,
"name": "Dalton Norman"
},
{
"user_id": 1,
"name": "Barrett Morales"
},
{
"user_id": 2,
"name": "Daniels Booth"
},
{
"user_id": 3,
"name": "Maxwell Rich"
},
{
"user_id": 4,
"name": "Bennett Washington"
},
{
"user_id": 5,
"name": "Lelia Banks"
},
{
"user_id": 6,
"name": "Georgette Joyce"
},
{
"user_id": 7,
"name": "Kaitlin Irwin"
},
{
"user_id": 8,
"name": "Lacey Case"
},
{
"user_id": 9,
"name": "Reyes Jenkins"
},
{
"user_id": 10,
"name": "Rios Dunn"
},
{
"user_id": 11,
"name": "Walsh Robles"
},
{
"user_id": 12,
"name": "Nieves Ratliff"
},
{
"user_id": 13,
"name": "Alta Brennan"
},
{
"user_id": 14,
"name": "Theresa Gilliam"
}
]
},
{
"user_id": 13,
"name": "Cantu Griffin",
"children": [
{
"user_id": 0,
"name": "Gilmore Jordan"
},
{
"user_id": 1,
"name": "Mindy Mercado"
},
{
"user_id": 2,
"name": "Townsend Harmon"
},
{
"user_id": 3,
"name": "Bethany Mathis"
},
{
"user_id": 4,
"name": "Tonia Patel"
},
{
"user_id": 5,
"name": "Earnestine Foster"
},
{
"user_id": 6,
"name": "Wilson Evans"
},
{
"user_id": 7,
"name": "Olsen Wheeler"
},
{
"user_id": 8,
"name": "Mejia Hall"
},
{
"user_id": 9,
"name": "Viola Waller"
},
{
"user_id": 10,
"name": "Robbins Rivera"
},
{
"user_id": 11,
"name": "Lowe Yang"
},
{
"user_id": 12,
"name": "Riddle Cervantes"
},
{
"user_id": 13,
"name": "Rachel Soto"
},
{
"user_id": 14,
"name": "Gonzales Bond"
}
]
}
]
},
{
"user_id": 10,
"name": "Rosario Molina",
"children": [
{
"user_id": 0,
"name": "Robyn Garza",
"children": [
{
"user_id": 0,
"name": "Mable Hines"
},
{
"user_id": 1,
"name": "Angelica Mcdaniel"
},
{
"user_id": 2,
"name": "Raquel Cervantes"
},
{
"user_id": 3,
"name": "Nona Mcfadden"
},
{
"user_id": 4,
"name": "Pearl Mclaughlin"
},
{
"user_id": 5,
"name": "Bessie Ferguson"
},
{
"user_id": 6,
"name": "Gutierrez Collier"
},
{
"user_id": 7,
"name": "Rosanna Hopper"
},
{
"user_id": 8,
"name": "Eleanor Barlow"
},
{
"user_id": 9,
"name": "Krystal Wiley"
},
{
"user_id": 10,
"name": "Amalia Whitney"
},
{
"user_id": 11,
"name": "Hunt Dennis"
},
{
"user_id": 12,
"name": "Hobbs Doyle"
},
{
"user_id": 13,
"name": "Clarissa Bates"
},
{
"user_id": 14,
"name": "Ada Beck"
}
]
},
{
"user_id": 1,
"name": "Candace Gomez",
"children": [
{
"user_id": 0,
"name": "Bette Bolton"
},
{
"user_id": 1,
"name": "Mendoza Emerson"
},
{
"user_id": 2,
"name": "Natalie Powers"
},
{
"user_id": 3,
"name": "Bowen Massey"
},
{
"user_id": 4,
"name": "Lucia Hardy"
},
{
"user_id": 5,
"name": "Tillman Willis"
},
{
"user_id": 6,
"name": "Vinson Mcgowan"
},
{
"user_id": 7,
"name": "Leta Hoover"
},
{
"user_id": 8,
"name": "Barnett Gallegos"
},
{
"user_id": 9,
"name": "Keisha Bowen"
},
{
"user_id": 10,
"name": "Sharp Berger"
},
{
"user_id": 11,
"name": "Bates Davenport"
},
{
"user_id": 12,
"name": "Stuart Levy"
},
{
"user_id": 13,
"name": "Aurora Mercado"
},
{
"user_id": 14,
"name": "Callahan Sellers"
}
]
},
{
"user_id": 2,
"name": "Sharlene Mueller",
"children": [
{
"user_id": 0,
"name": "Selena Mooney"
},
{
"user_id": 1,
"name": "Iva Woodard"
},
{
"user_id": 2,
"name": "Olga Zimmerman"
},
{
"user_id": 3,
"name": "Christi Townsend"
},
{
"user_id": 4,
"name": "Augusta Rollins"
},
{
"user_id": 5,
"name": "Powell Bass"
},
{
"user_id": 6,
"name": "Morton Myers"
},
{
"user_id": 7,
"name": "Thompson Lowery"
},
{
"user_id": 8,
"name": "Sharon Soto"
},
{
"user_id": 9,
"name": "Maddox Potts"
},
{
"user_id": 10,
"name": "Heath Mayo"
},
{
"user_id": 11,
"name": "Oneal Bridges"
},
{
"user_id": 12,
"name": "Irene Conley"
},
{
"user_id": 13,
"name": "House Montoya"
},
{
"user_id": 14,
"name": "Jo Deleon"
}
]
},
{
"user_id": 3,
"name": "Erica Grimes",
"children": [
{
"user_id": 0,
"name": "Gloria Chapman"
},
{
"user_id": 1,
"name": "Vasquez Snyder"
},
{
"user_id": 2,
"name": "Ofelia Mclean"
},
{
"user_id": 3,
"name": "Jimenez Harvey"
},
{
"user_id": 4,
"name": "Jocelyn Joyner"
},
{
"user_id": 5,
"name": "Desiree Shaffer"
},
{
"user_id": 6,
"name": "Jana Delgado"
},
{
"user_id": 7,
"name": "Potter Mendez"
},
{
"user_id": 8,
"name": "Mallory Atkinson"
},
{
"user_id": 9,
"name": "Sabrina Tanner"
},
{
"user_id": 10,
"name": "Guerrero Mccall"
},
{
"user_id": 11,
"name": "Collier Trujillo"
},
{
"user_id": 12,
"name": "Pope Rivers"
},
{
"user_id": 13,
"name": "Jackson Ellison"
},
{
"user_id": 14,
"name": "Mcintosh Sosa"
}
]
},
{
"user_id": 4,
"name": "Wolfe Glenn",
"children": [
{
"user_id": 0,
"name": "Santana Johns"
},
{
"user_id": 1,
"name": "Rosemarie Castro"
},
{
"user_id": 2,
"name": "Mason Hanson"
},
{
"user_id": 3,
"name": "Luann Carter"
},
{
"user_id": 4,
"name": "Cherry George"
},
{
"user_id": 5,
"name": "Kirsten Munoz"
},
{
"user_id": 6,
"name": "Jacquelyn Stevens"
},
{
"user_id": 7,
"name": "Pat Witt"
},
{
"user_id": 8,
"name": "Romero Dixon"
},
{
"user_id": 9,
"name": "Washington Hurst"
},
{
"user_id": 10,
"name": "Mueller Sharpe"
},
{
"user_id": 11,
"name": "Avis Mccarthy"
},
{
"user_id": 12,
"name": "Erma Slater"
},
{
"user_id": 13,
"name": "Imogene Pearson"
},
{
"user_id": 14,
"name": "Marquez Contreras"
}
]
},
{
"user_id": 5,
"name": "Bond Hampton",
"children": [
{
"user_id": 0,
"name": "Jenny Bowers"
},
{
"user_id": 1,
"name": "Meadows Pope"
},
{
"user_id": 2,
"name": "Beck Cruz"
},
{
"user_id": 3,
"name": "Barbara Mcmahon"
},
{
"user_id": 4,
"name": "Ashley Morales"
},
{
"user_id": 5,
"name": "Ernestine Hinton"
},
{
"user_id": 6,
"name": "Hawkins Castillo"
},
{
"user_id": 7,
"name": "Carey Rowe"
},
{
"user_id": 8,
"name": "Whitaker Norman"
},
{
"user_id": 9,
"name": "Inez Ellis"
},
{
"user_id": 10,
"name": "Shauna Bryan"
},
{
"user_id": 11,
"name": "White Lawson"
},
{
"user_id": 12,
"name": "Lynnette Ware"
},
{
"user_id": 13,
"name": "Clements Barton"
},
{
"user_id": 14,
"name": "Armstrong Moon"
}
]
},
{
"user_id": 6,
"name": "Marguerite Hensley",
"children": [
{
"user_id": 0,
"name": "Wise Knowles"
},
{
"user_id": 1,
"name": "Kristy Jordan"
},
{
"user_id": 2,
"name": "Hodge Wilder"
},
{
"user_id": 3,
"name": "Jewel Fuller"
},
{
"user_id": 4,
"name": "Horne Luna"
},
{
"user_id": 5,
"name": "Mamie Acevedo"
},
{
"user_id": 6,
"name": "Drake Holder"
},
{
"user_id": 7,
"name": "Silva Yang"
},
{
"user_id": 8,
"name": "Wiggins Rodgers"
},
{
"user_id": 9,
"name": "Tamara Cohen"
},
{
"user_id": 10,
"name": "Leslie Mayer"
},
{
"user_id": 11,
"name": "Georgia Daniels"
},
{
"user_id": 12,
"name": "Julie Hansen"
},
{
"user_id": 13,
"name": "Gail Mullen"
},
{
"user_id": 14,
"name": "Diane Cummings"
}
]
},
{
"user_id": 7,
"name": "Myrtle Bartlett",
"children": [
{
"user_id": 0,
"name": "Jones Harrison"
},
{
"user_id": 1,
"name": "Carlson Pugh"
},
{
"user_id": 2,
"name": "Browning Shaw"
},
{
"user_id": 3,
"name": "Rosario Lamb"
},
{
"user_id": 4,
"name": "Ramos Evans"
},
{
"user_id": 5,
"name": "Rosalyn Rowland"
},
{
"user_id": 6,
"name": "Kerr Gilliam"
},
{
"user_id": 7,
"name": "Madden Kline"
},
{
"user_id": 8,
"name": "Todd West"
},
{
"user_id": 9,
"name": "Gwen Foster"
},
{
"user_id": 10,
"name": "Maude Melendez"
},
{
"user_id": 11,
"name": "Hanson Jacobs"
},
{
"user_id": 12,
"name": "Foreman Parsons"
},
{
"user_id": 13,
"name": "Ericka Holden"
},
{
"user_id": 14,
"name": "Mckay Keller"
}
]
},
{
"user_id": 8,
"name": "Imelda Oliver",
"children": [
{
"user_id": 0,
"name": "Alana Levine"
},
{
"user_id": 1,
"name": "Navarro Hernandez"
},
{
"user_id": 2,
"name": "Kim Torres"
},
{
"user_id": 3,
"name": "Virgie Hawkins"
},
{
"user_id": 4,
"name": "Angela Vang"
},
{
"user_id": 5,
"name": "Kellie Yates"
},
{
"user_id": 6,
"name": "Lenora Rodriguez"
},
{
"user_id": 7,
"name": "Cameron Burch"
},
{
"user_id": 8,
"name": "Chris Huffman"
},
{
"user_id": 9,
"name": "Reyna Gillespie"
},
{
"user_id": 10,
"name": "Sheila Richardson"
},
{
"user_id": 11,
"name": "Sutton Maddox"
},
{
"user_id": 12,
"name": "Salas Cross"
},
{
"user_id": 13,
"name": "Miranda Clarke"
},
{
"user_id": 14,
"name": "Sheppard Wynn"
}
]
},
{
"user_id": 9,
"name": "Martinez Walsh",
"children": [
{
"user_id": 0,
"name": "Bettye Romero"
},
{
"user_id": 1,
"name": "Michelle Avery"
},
{
"user_id": 2,
"name": "Oneil Pacheco"
},
{
"user_id": 3,
"name": "Hicks Sloan"
},
{
"user_id": 4,
"name": "Caldwell Woodward"
},
{
"user_id": 5,
"name": "Booker Finch"
},
{
"user_id": 6,
"name": "Shawna Mckee"
},
{
"user_id": 7,
"name": "Delia Olson"
},
{
"user_id": 8,
"name": "Nina Crawford"
},
{
"user_id": 9,
"name": "Marcie Whitley"
},
{
"user_id": 10,
"name": "Lewis Morin"
},
{
"user_id": 11,
"name": "Liz Parrish"
},
{
"user_id": 12,
"name": "Adrian Lynch"
},
{
"user_id": 13,
"name": "Massey Nash"
},
{
"user_id": 14,
"name": "Victoria Vance"
}
]
},
{
"user_id": 10,
"name": "Rosella Ramsey",
"children": [
{
"user_id": 0,
"name": "Hillary Hyde"
},
{
"user_id": 1,
"name": "Flossie Gentry"
},
{
"user_id": 2,
"name": "Atkins Huber"
},
{
"user_id": 3,
"name": "Lowe Brennan"
},
{
"user_id": 4,
"name": "Hale Melton"
},
{
"user_id": 5,
"name": "Betty Ball"
},
{
"user_id": 6,
"name": "Compton Nixon"
},
{
"user_id": 7,
"name": "Jacobs Sanchez"
},
{
"user_id": 8,
"name": "Campbell Cochran"
},
{
"user_id": 9,
"name": "Dorsey Hubbard"
},
{
"user_id": 10,
"name": "Ramona Tucker"
},
{
"user_id": 11,
"name": "Weaver Jacobson"
},
{
"user_id": 12,
"name": "Wade Cantu"
},
{
"user_id": 13,
"name": "Harvey Collins"
},
{
"user_id": 14,
"name": "Marisa Harmon"
}
]
},
{
"user_id": 11,
"name": "Randolph Humphrey",
"children": [
{
"user_id": 0,
"name": "Dora Warner"
},
{
"user_id": 1,
"name": "Adriana Richmond"
},
{
"user_id": 2,
"name": "Lelia Macdonald"
},
{
"user_id": 3,
"name": "Elma Bean"
},
{
"user_id": 4,
"name": "Richards Park"
},
{
"user_id": 5,
"name": "Lara Weber"
},
{
"user_id": 6,
"name": "Puckett Delacruz"
},
{
"user_id": 7,
"name": "Lakisha Day"
},
{
"user_id": 8,
"name": "Goodman Palmer"
},
{
"user_id": 9,
"name": "Lina Newton"
},
{
"user_id": 10,
"name": "Jeannette Oneill"
},
{
"user_id": 11,
"name": "Ray Sears"
},
{
"user_id": 12,
"name": "Mooney Pierce"
},
{
"user_id": 13,
"name": "Clay Randolph"
},
{
"user_id": 14,
"name": "Denise Savage"
}
]
},
{
"user_id": 12,
"name": "Carey Arnold",
"children": [
{
"user_id": 0,
"name": "Cooper Scott"
},
{
"user_id": 1,
"name": "Edwina Rosario"
},
{
"user_id": 2,
"name": "Cassie Butler"
},
{
"user_id": 3,
"name": "Hogan Buckley"
},
{
"user_id": 4,
"name": "Betsy Reed"
},
{
"user_id": 5,
"name": "Beasley Schneider"
},
{
"user_id": 6,
"name": "Luella Walker"
},
{
"user_id": 7,
"name": "Woodard Avila"
},
{
"user_id": 8,
"name": "Dominique Wise"
},
{
"user_id": 9,
"name": "Wendi Burns"
},
{
"user_id": 10,
"name": "Dana Copeland"
},
{
"user_id": 11,
"name": "Martina Hickman"
},
{
"user_id": 12,
"name": "Mcclain Powell"
},
{
"user_id": 13,
"name": "Woods Hahn"
},
{
"user_id": 14,
"name": "Sloan Reid"
}
]
},
{
"user_id": 13,
"name": "Latasha Waller",
"children": [
{
"user_id": 0,
"name": "Parks Murray"
},
{
"user_id": 1,
"name": "Rowena Taylor"
},
{
"user_id": 2,
"name": "Alford Vincent"
},
{
"user_id": 3,
"name": "Gena Cote"
},
{
"user_id": 4,
"name": "Wilkins Solomon"
},
{
"user_id": 5,
"name": "Gallagher Barnett"
},
{
"user_id": 6,
"name": "Darla Spencer"
},
{
"user_id": 7,
"name": "Stokes Calhoun"
},
{
"user_id": 8,
"name": "Wallace Moore"
},
{
"user_id": 9,
"name": "Barnes White"
},
{
"user_id": 10,
"name": "Bridges English"
},
{
"user_id": 11,
"name": "Lindsey Hester"
},
{
"user_id": 12,
"name": "Marsh Guerrero"
},
{
"user_id": 13,
"name": "Williamson Noble"
},
{
"user_id": 14,
"name": "Lavonne Nelson"
}
]
},
{
"user_id": 14,
"name": "Blanca Holmes",
"children": [
{
"user_id": 0,
"name": "Cynthia Tran"
},
{
"user_id": 1,
"name": "Tamra Carver"
},
{
"user_id": 2,
"name": "Oconnor Acosta"
},
{
"user_id": 3,
"name": "Maxine Ratliff"
},
{
"user_id": 4,
"name": "Lindsay Cannon"
},
{
"user_id": 5,
"name": "Carney Harrington"
},
{
"user_id": 6,
"name": "Millie Roach"
},
{
"user_id": 7,
"name": "Waters Odom"
},
{
"user_id": 8,
"name": "Heidi Gill"
},
{
"user_id": 9,
"name": "Gracie Guzman"
},
{
"user_id": 10,
"name": "Grant Mack"
},
{
"user_id": 11,
"name": "Rosalinda Webb"
},
{
"user_id": 12,
"name": "Jarvis Whitfield"
},
{
"user_id": 13,
"name": "Veronica Stein"
},
{
"user_id": 14,
"name": "Harmon Kidd"
}
]
}
]
}
]
},
{
"user_id": 1,
"name": "Constance Prince",
"children": [
{
"user_id": 1,
"name": "Faith Phelps",
"children": [
{
"user_id": 0,
"name": "Mcgowan Fernandez",
"children": [
{
"user_id": 0,
"name": "Rollins Joyce"
},
{
"user_id": 1,
"name": "Shawna Ortiz"
},
{
"user_id": 2,
"name": "Dorothy Frank"
},
{
"user_id": 3,
"name": "Wyatt Hays"
},
{
"user_id": 4,
"name": "Barrett Haney"
},
{
"user_id": 5,
"name": "Francesca Kinney"
},
{
"user_id": 6,
"name": "Brady Cohen"
},
{
"user_id": 7,
"name": "Tanner Lloyd"
},
{
"user_id": 8,
"name": "Adkins Page"
},
{
"user_id": 9,
"name": "Janette Anthony"
},
{
"user_id": 10,
"name": "Alberta Solomon"
},
{
"user_id": 11,
"name": "Stout Santana"
},
{
"user_id": 12,
"name": "Stuart Decker"
},
{
"user_id": 13,
"name": "Oconnor Wallace"
},
{
"user_id": 14,
"name": "Wendy Farrell"
}
]
},
{
"user_id": 1,
"name": "Pickett Sherman",
"children": [
{
"user_id": 0,
"name": "Vang Salinas"
},
{
"user_id": 1,
"name": "Alvarado Sanchez"
},
{
"user_id": 2,
"name": "Hanson Giles"
},
{
"user_id": 3,
"name": "Eloise Miranda"
},
{
"user_id": 4,
"name": "May Douglas"
},
{
"user_id": 5,
"name": "Johanna Ellis"
},
{
"user_id": 6,
"name": "Irma Chang"
},
{
"user_id": 7,
"name": "Violet Horn"
},
{
"user_id": 8,
"name": "Christi Townsend"
},
{
"user_id": 9,
"name": "Jerry Patrick"
},
{
"user_id": 10,
"name": "Morrison Morales"
},
{
"user_id": 11,
"name": "Terrell Schneider"
},
{
"user_id": 12,
"name": "Katherine Blair"
},
{
"user_id": 13,
"name": "Walters Dean"
},
{
"user_id": 14,
"name": "Penelope Hinton"
}
]
},
{
"user_id": 2,
"name": "Jerri Evans",
"children": [
{
"user_id": 0,
"name": "Dawson Levine"
},
{
"user_id": 1,
"name": "Tracie Levy"
},
{
"user_id": 2,
"name": "Walton Kidd"
},
{
"user_id": 3,
"name": "Mueller Sykes"
},
{
"user_id": 4,
"name": "Knapp Hunt"
},
{
"user_id": 5,
"name": "Hoover Rojas"
},
{
"user_id": 6,
"name": "Iva Hernandez"
},
{
"user_id": 7,
"name": "Irene Blankenship"
},
{
"user_id": 8,
"name": "Sosa Ochoa"
},
{
"user_id": 9,
"name": "Knight Black"
},
{
"user_id": 10,
"name": "Olivia Peters"
},
{
"user_id": 11,
"name": "Fernandez Fletcher"
},
{
"user_id": 12,
"name": "Jamie Underwood"
},
{
"user_id": 13,
"name": "Montoya Hartman"
},
{
"user_id": 14,
"name": "Rosemary Castro"
}
]
},
{
"user_id": 3,
"name": "Hurley Dunn",
"children": [
{
"user_id": 0,
"name": "Rodgers Ellison"
},
{
"user_id": 1,
"name": "Richard Whitney"
},
{
"user_id": 2,
"name": "Haley Boyle"
},
{
"user_id": 3,
"name": "Jefferson Brown"
},
{
"user_id": 4,
"name": "Stacey Brock"
},
{
"user_id": 5,
"name": "Melba House"
},
{
"user_id": 6,
"name": "Charles Frost"
},
{
"user_id": 7,
"name": "Schmidt Holcomb"
},
{
"user_id": 8,
"name": "Liz Martinez"
},
{
"user_id": 9,
"name": "Summers Estrada"
},
{
"user_id": 10,
"name": "Pittman Lawson"
},
{
"user_id": 11,
"name": "Whitfield Dennis"
},
{
"user_id": 12,
"name": "Travis Chapman"
},
{
"user_id": 13,
"name": "Amy Hester"
},
{
"user_id": 14,
"name": "Willie Davidson"
}
]
},
{
"user_id": 4,
"name": "Shelia Rogers",
"children": [
{
"user_id": 0,
"name": "Knox Ferguson"
},
{
"user_id": 1,
"name": "Hansen Carey"
},
{
"user_id": 2,
"name": "Misty Weber"
},
{
"user_id": 3,
"name": "Diane Peterson"
},
{
"user_id": 4,
"name": "Gracie Yang"
},
{
"user_id": 5,
"name": "Campos Bradford"
},
{
"user_id": 6,
"name": "Jo Cabrera"
},
{
"user_id": 7,
"name": "Angie Compton"
},
{
"user_id": 8,
"name": "Chase Miles"
},
{
"user_id": 9,
"name": "Donaldson Pittman"
},
{
"user_id": 10,
"name": "Reba Vance"
},
{
"user_id": 11,
"name": "Dominique Blackwell"
},
{
"user_id": 12,
"name": "Mildred Tillman"
},
{
"user_id": 13,
"name": "Obrien Fields"
},
{
"user_id": 14,
"name": "Margret Hebert"
}
]
},
{
"user_id": 5,
"name": "Mann Nolan",
"children": [
{
"user_id": 0,
"name": "Earline Ayers"
},
{
"user_id": 1,
"name": "Eddie Davenport"
},
{
"user_id": 2,
"name": "Alana Mann"
},
{
"user_id": 3,
"name": "Rosanna Norris"
},
{
"user_id": 4,
"name": "Fisher Gray"
},
{
"user_id": 5,
"name": "Rowland Velazquez"
},
{
"user_id": 6,
"name": "Nanette Dawson"
},
{
"user_id": 7,
"name": "Maureen Murray"
},
{
"user_id": 8,
"name": "Ashley Joseph"
},
{
"user_id": 9,
"name": "Bonner Mercado"
},
{
"user_id": 10,
"name": "Elise Woodward"
},
{
"user_id": 11,
"name": "Bianca Colon"
},
{
"user_id": 12,
"name": "Johnson Gilbert"
},
{
"user_id": 13,
"name": "Dixon Neal"
},
{
"user_id": 14,
"name": "Karen Thornton"
}
]
},
{
"user_id": 6,
"name": "Vaughn Guthrie",
"children": [
{
"user_id": 0,
"name": "Henrietta Norman"
},
{
"user_id": 1,
"name": "Maldonado Peck"
},
{
"user_id": 2,
"name": "Pitts Snider"
},
{
"user_id": 3,
"name": "Ingrid Simpson"
},
{
"user_id": 4,
"name": "Bridgett Pena"
},
{
"user_id": 5,
"name": "Adams Davis"
},
{
"user_id": 6,
"name": "Larson Petersen"
},
{
"user_id": 7,
"name": "Goldie Strong"
},
{
"user_id": 8,
"name": "Sandy Hood"
},
{
"user_id": 9,
"name": "Garrison Knapp"
},
{
"user_id": 10,
"name": "Leann Hickman"
},
{
"user_id": 11,
"name": "Franco Fischer"
},
{
"user_id": 12,
"name": "Tabitha Sawyer"
},
{
"user_id": 13,
"name": "Porter Willis"
},
{
"user_id": 14,
"name": "Chan Floyd"
}
]
},
{
"user_id": 7,
"name": "Wood Schroeder",
"children": [
{
"user_id": 0,
"name": "Yesenia Rice"
},
{
"user_id": 1,
"name": "Sharon Vaughn"
},
{
"user_id": 2,
"name": "Ward Fuentes"
},
{
"user_id": 3,
"name": "Reese Adkins"
},
{
"user_id": 4,
"name": "Henderson Brooks"
},
{
"user_id": 5,
"name": "Davidson Pope"
},
{
"user_id": 6,
"name": "Toni Richardson"
},
{
"user_id": 7,
"name": "Colleen Atkins"
},
{
"user_id": 8,
"name": "Webster Gilliam"
},
{
"user_id": 9,
"name": "Muriel Goodman"
},
{
"user_id": 10,
"name": "Hooper Daniels"
},
{
"user_id": 11,
"name": "Farrell Rivera"
},
{
"user_id": 12,
"name": "Rae Wiley"
},
{
"user_id": 13,
"name": "Abigail Williamson"
},
{
"user_id": 14,
"name": "Kline Benton"
}
]
},
{
"user_id": 8,
"name": "Joan Ryan",
"children": [
{
"user_id": 0,
"name": "Kelley Carney"
},
{
"user_id": 1,
"name": "Tiffany Nicholson"
},
{
"user_id": 2,
"name": "Brennan Casey"
},
{
"user_id": 3,
"name": "Neal Osborn"
},
{
"user_id": 4,
"name": "Miranda Dodson"
},
{
"user_id": 5,
"name": "Thompson Mcfarland"
},
{
"user_id": 6,
"name": "Fleming Rutledge"
},
{
"user_id": 7,
"name": "Bernadette Jacobson"
},
{
"user_id": 8,
"name": "Petra Hicks"
},
{
"user_id": 9,
"name": "Marquez Michael"
},
{
"user_id": 10,
"name": "Donovan Bryan"
},
{
"user_id": 11,
"name": "Hope Morton"
},
{
"user_id": 12,
"name": "Elvira Cotton"
},
{
"user_id": 13,
"name": "Frankie Tran"
},
{
"user_id": 14,
"name": "Guy Griffith"
}
]
},
{
"user_id": 9,
"name": "Talley Simmons",
"children": [
{
"user_id": 0,
"name": "Bass Mcdowell"
},
{
"user_id": 1,
"name": "Ofelia Montoya"
},
{
"user_id": 2,
"name": "Agnes Nelson"
},
{
"user_id": 3,
"name": "Tamera Hill"
},
{
"user_id": 4,
"name": "Miranda Ruiz"
},
{
"user_id": 5,
"name": "Mcdaniel Barnett"
},
{
"user_id": 6,
"name": "Rich Bean"
},
{
"user_id": 7,
"name": "Hines Griffin"
},
{
"user_id": 8,
"name": "Erna Farley"
},
{
"user_id": 9,
"name": "Burgess Scott"
},
{
"user_id": 10,
"name": "Chris Howe"
},
{
"user_id": 11,
"name": "Tammie Cline"
},
{
"user_id": 12,
"name": "Booth Sexton"
},
{
"user_id": 13,
"name": "Harper Durham"
},
{
"user_id": 14,
"name": "Dollie May"
}
]
},
{
"user_id": 10,
"name": "Alicia Glass",
"children": [
{
"user_id": 0,
"name": "Cheryl Conrad"
},
{
"user_id": 1,
"name": "Patti Miller"
},
{
"user_id": 2,
"name": "Neva Mcgowan"
},
{
"user_id": 3,
"name": "Hutchinson Whitehead"
},
{
"user_id": 4,
"name": "Kate Vaughn"
},
{
"user_id": 5,
"name": "Hogan Barrett"
},
{
"user_id": 6,
"name": "Tami Conway"
},
{
"user_id": 7,
"name": "Michael Velez"
},
{
"user_id": 8,
"name": "Cornelia Brewer"
},
{
"user_id": 9,
"name": "Thompson Watkins"
},
{
"user_id": 10,
"name": "Morrow Cabrera"
},
{
"user_id": 11,
"name": "Rose Berg"
},
{
"user_id": 12,
"name": "Case Kerr"
},
{
"user_id": 13,
"name": "Imelda Rivas"
},
{
"user_id": 14,
"name": "Frances Wyatt"
}
]
},
{
"user_id": 11,
"name": "Weaver Beck",
"children": [
{
"user_id": 0,
"name": "Kimberly Osborne"
},
{
"user_id": 1,
"name": "Hannah Carey"
},
{
"user_id": 2,
"name": "Emily Mcintyre"
},
{
"user_id": 3,
"name": "Melba Horn"
},
{
"user_id": 4,
"name": "Serena Perez"
},
{
"user_id": 5,
"name": "Johnnie Holder"
},
{
"user_id": 6,
"name": "Wiggins Greer"
},
{
"user_id": 7,
"name": "Weiss Peters"
},
{
"user_id": 8,
"name": "Barrett Rutledge"
},
{
"user_id": 9,
"name": "Burris Hebert"
},
{
"user_id": 10,
"name": "Chrystal Vasquez"
},
{
"user_id": 11,
"name": "Zamora Rodriquez"
},
{
"user_id": 12,
"name": "Laurie Benjamin"
},
{
"user_id": 13,
"name": "Alice Rodgers"
},
{
"user_id": 14,
"name": "Susie Blankenship"
}
]
},
{
"user_id": 12,
"name": "Lindsay Cohen",
"children": [
{
"user_id": 0,
"name": "Sanders Shaw"
},
{
"user_id": 1,
"name": "Clay Madden"
},
{
"user_id": 2,
"name": "Sheena Merrill"
},
{
"user_id": 3,
"name": "Kris Graham"
},
{
"user_id": 4,
"name": "Adrian Morales"
},
{
"user_id": 5,
"name": "Vickie Everett"
},
{
"user_id": 6,
"name": "Abbott Calhoun"
},
{
"user_id": 7,
"name": "Hayes Leonard"
},
{
"user_id": 8,
"name": "Gould Brock"
},
{
"user_id": 9,
"name": "Vinson Fowler"
},
{
"user_id": 10,
"name": "Chambers Howell"
},
{
"user_id": 11,
"name": "Darla Bradshaw"
},
{
"user_id": 12,
"name": "Nancy Marshall"
},
{
"user_id": 13,
"name": "Leann Harper"
},
{
"user_id": 14,
"name": "Cindy Wilcox"
}
]
},
{
"user_id": 13,
"name": "Glenda Dickerson",
"children": [
{
"user_id": 0,
"name": "Melanie Reyes"
},
{
"user_id": 1,
"name": "Ada Rhodes"
},
{
"user_id": 2,
"name": "Ursula Santos"
},
{
"user_id": 3,
"name": "Lesley Gibson"
},
{
"user_id": 4,
"name": "Frazier Gillespie"
},
{
"user_id": 5,
"name": "Rosanne Clayton"
},
{
"user_id": 6,
"name": "Noemi Carver"
},
{
"user_id": 7,
"name": "Young Massey"
},
{
"user_id": 8,
"name": "King Hutchinson"
},
{
"user_id": 9,
"name": "Sharron Patterson"
},
{
"user_id": 10,
"name": "Browning Gates"
},
{
"user_id": 11,
"name": "Renee Vance"
},
{
"user_id": 12,
"name": "Kristina Wheeler"
},
{
"user_id": 13,
"name": "Bowers Macdonald"
},
{
"user_id": 14,
"name": "Russo Cross"
}
]
},
{
"user_id": 14,
"name": "Sykes Rosa",
"children": [
{
"user_id": 0,
"name": "Sellers Ingram"
},
{
"user_id": 1,
"name": "Marietta Shelton"
},
{
"user_id": 2,
"name": "Cummings Carroll"
},
{
"user_id": 3,
"name": "Lucas Reilly"
},
{
"user_id": 4,
"name": "Jane Hester"
},
{
"user_id": 5,
"name": "Amanda Walsh"
},
{
"user_id": 6,
"name": "Christian Sanchez"
},
{
"user_id": 7,
"name": "Audrey Alexander"
},
{
"user_id": 8,
"name": "Emma Park"
},
{
"user_id": 9,
"name": "Angelita Vang"
},
{
"user_id": 10,
"name": "Shawna Bray"
},
{
"user_id": 11,
"name": "Herring Pena"
},
{
"user_id": 12,
"name": "Wilma Dixon"
},
{
"user_id": 13,
"name": "Jerri Kemp"
},
{
"user_id": 14,
"name": "Rush Price"
}
]
}
]
},
{
"user_id": 2,
"name": "Young Levine",
"children": [
{
"user_id": 5,
"name": "Chaney Bell",
"children": [
{
"user_id": 0,
"name": "Elma Bass"
},
{
"user_id": 1,
"name": "Marylou Guy"
},
{
"user_id": 2,
"name": "Brooke Baird"
},
{
"user_id": 3,
"name": "Kathryn Stout"
},
{
"user_id": 4,
"name": "Holman Pugh"
},
{
"user_id": 5,
"name": "Lawson Blackwell"
},
{
"user_id": 6,
"name": "Lily Strong"
},
{
"user_id": 7,
"name": "Sharon Duffy"
},
{
"user_id": 8,
"name": "Bennett Cook"
},
{
"user_id": 9,
"name": "Ines Conley"
},
{
"user_id": 10,
"name": "Ross Reid"
},
{
"user_id": 11,
"name": "Leach Pratt"
},
{
"user_id": 12,
"name": "Lilly Cole"
},
{
"user_id": 13,
"name": "Schultz Hart"
},
{
"user_id": 14,
"name": "Gilbert Gilbert"
}
]
},
{
"user_id": 11,
"name": "Carey Odonnell",
"children": [
{
"user_id": 0,
"name": "Robinson Vazquez"
},
{
"user_id": 1,
"name": "Mandy Wise"
},
{
"user_id": 2,
"name": "Mcclain Sanford"
},
{
"user_id": 3,
"name": "Taylor Wooten"
},
{
"user_id": 4,
"name": "Weber Best"
},
{
"user_id": 5,
"name": "Cecelia Henson"
},
{
"user_id": 6,
"name": "Rhonda Baker"
},
{
"user_id": 7,
"name": "Cara Gregory"
},
{
"user_id": 8,
"name": "James Walter"
},
{
"user_id": 9,
"name": "Christa Roth"
},
{
"user_id": 10,
"name": "Stevenson Rodriguez"
},
{
"user_id": 11,
"name": "Johanna Cummings"
},
{
"user_id": 12,
"name": "Vanessa Collins"
},
{
"user_id": 13,
"name": "Davidson Meyer"
},
{
"user_id": 14,
"name": "Peggy King"
}
]
},
{
"user_id": 13,
"name": "Anna Forbes",
"children": [
{
"user_id": 0,
"name": "Jeanne Romero"
},
{
"user_id": 1,
"name": "Kelley Keller"
},
{
"user_id": 2,
"name": "Kaitlin Mathis"
},
{
"user_id": 3,
"name": "Gordon Keith"
},
{
"user_id": 4,
"name": "Mavis Parker"
},
{
"user_id": 5,
"name": "Dejesus Walls"
},
{
"user_id": 6,
"name": "Ratliff Shaffer"
},
{
"user_id": 7,
"name": "Maryellen Gomez"
},
{
"user_id": 8,
"name": "Hudson Christian"
},
{
"user_id": 9,
"name": "Natalia Bond"
},
{
"user_id": 10,
"name": "Newton Pitts"
},
{
"user_id": 11,
"name": "Matilda Rivera"
},
{
"user_id": 12,
"name": "Palmer Pickett"
},
{
"user_id": 13,
"name": "Bradley Mckinney"
},
{
"user_id": 14,
"name": "Shelia Galloway"
}
]
}
]
}
]
}
]
};
// Get JSON data
//treeJSON = d3.json('hey', function(error, treeData) {
// Calculate total nodes, max label length
var totalNodes = 0;
var maxLabelLength = 0;
// variables for drag/drop
var selectedNode = null;
var draggingNode = null;
// panning variables
var panSpeed = 200;
var panBoundary = 20; // Within 20px from edges will pan when dragging.
// Misc. variables
var i = 0;
var duration = 750;
var root;
// size of the diagram
var viewerWidth = $(document).width();
var viewerHeight = $(document).height();
var tree = d3.layout.tree()
.size([viewerHeight, viewerWidth]);
// define a d3 diagonal projection for use by the node paths later on.
var diagonal = d3.svg.diagonal()
.projection(function(d) {
return [d.y, d.x];
});
// A recursive helper function for performing some setup by walking through all nodes
function visit(parent, visitFn, childrenFn) {
if (!parent) return;
visitFn(parent);
var children = childrenFn(parent);
if (children) {
var count = children.length;
for (var i = 0; i < count; i++) {
visit(children[i], visitFn, childrenFn);
}
}
}
// Call visit function to establish maxLabelLength
visit(treeData, function(d) {
totalNodes++;
console.log(d);
maxLabelLength = 10;
console.log("after");
}, function(d) {
return d.children && d.children.length > 0 ? d.children : null;
});
// sort the tree according to the node names
function sortTree() {
tree.sort(function(a, b) {
if (b.name !== undefined && a.name !== undefined) {
return b.name.toLowerCase() < a.name.toLowerCase() ? 1 : -1;
} else {
return 100000;
}
});
}
// Sort the tree initially incase the JSON isn't in a sorted order.
sortTree();
// TODO: Pan function, can be better implemented.
function pan(domNode, direction) {
var speed = panSpeed;
if (panTimer) {
clearTimeout(panTimer);
translateCoords = d3.transform(svgGroup.attr("transform"));
if (direction == 'left' || direction == 'right') {
translateX = direction == 'left' ? translateCoords.translate[0] + speed : translateCoords.translate[0] - speed;
translateY = translateCoords.translate[1];
} else if (direction == 'up' || direction == 'down') {
translateX = translateCoords.translate[0];
translateY = direction == 'up' ? translateCoords.translate[1] + speed : translateCoords.translate[1] - speed;
}
scaleX = translateCoords.scale[0];
scaleY = translateCoords.scale[1];
scale = zoomListener.scale();
svgGroup.transition().attr("transform", "translate(" + translateX + "," + translateY + ")scale(" + scale + ")");
d3.select(domNode).select('g.node').attr("transform", "translate(" + translateX + "," + translateY + ")");
zoomListener.scale(zoomListener.scale());
zoomListener.translate([translateX, translateY]);
panTimer = setTimeout(function() {
pan(domNode, speed, direction);
}, 50);
}
}
// Define the zoom function for the zoomable tree
function zoom() {
svgGroup.attr("transform", "translate(" + d3.event.translate + ")scale(" + d3.event.scale + ")");
}
// define the zoomListener which calls the zoom function on the "zoom" event constrained within the scaleExtents
var zoomListener = d3.behavior.zoom().scaleExtent([0.1, 3]).on("zoom", zoom);
function initiateDrag(d, domNode) {
draggingNode = d;
d3.select(domNode).select('.ghostCircle').attr('pointer-events', 'none');
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle show');
d3.select(domNode).attr('class', 'node activeDrag');
svgGroup.selectAll("g.node").sort(function(a, b) { // select the parent and sort the path's
if (a.id != draggingNode.id) return 1; // a is not the hovered element, send "a" to the back
else return -1; // a is the hovered element, bring "a" to the front
});
// if nodes has children, remove the links and nodes
if (nodes.length > 1) {
// remove link paths
links = tree.links(nodes);
nodePaths = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
}).remove();
// remove child nodes
nodesExit = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id;
}).filter(function(d, i) {
if (d.id == draggingNode.id) {
return false;
}
return true;
}).remove();
}
// remove parent link
parentLink = tree.links(tree.nodes(draggingNode.parent));
svgGroup.selectAll('path.link').filter(function(d, i) {
if (d.target.id == draggingNode.id) {
return true;
}
return false;
}).remove();
dragStarted = null;
}
// define the baseSvg, attaching a class for styling and the zoomListener
var baseSvg = d3.select("#tree-container").append("svg")
.attr("width", viewerWidth)
.attr("height", viewerHeight)
.attr("class", "overlay")
.call(zoomListener);
// Define the drag listeners for drag/drop behaviour of nodes.
dragListener = d3.behavior.drag()
.on("dragstart", function(d) {
if (d == root) {
return;
}
dragStarted = true;
nodes = tree.nodes(d);
d3.event.sourceEvent.stopPropagation();
// it's important that we suppress the mouseover event on the node being dragged. Otherwise it will absorb the mouseover event and the underlying node will not detect it d3.select(this).attr('pointer-events', 'none');
})
.on("drag", function(d) {
if (d == root) {
return;
}
if (dragStarted) {
domNode = this;
initiateDrag(d, domNode);
}
// get coords of mouseEvent relative to svg container to allow for panning
relCoords = d3.mouse($('svg').get(0));
if (relCoords[0] < panBoundary) {
panTimer = true;
pan(this, 'left');
} else if (relCoords[0] > ($('svg').width() - panBoundary)) {
panTimer = true;
pan(this, 'right');
} else if (relCoords[1] < panBoundary) {
panTimer = true;
pan(this, 'up');
} else if (relCoords[1] > ($('svg').height() - panBoundary)) {
panTimer = true;
pan(this, 'down');
} else {
try {
clearTimeout(panTimer);
} catch (e) {
}
}
d.x0 += d3.event.dy;
d.y0 += d3.event.dx;
var node = d3.select(this);
node.attr("transform", "translate(" + d.y0 + "," + d.x0 + ")");
updateTempConnector();
}).on("dragend", function(d) {
if (d == root) {
return;
}
domNode = this;
if (selectedNode) {
// now remove the element from the parent, and insert it into the new elements children
var index = draggingNode.parent.children.indexOf(draggingNode);
if (index > -1) {
draggingNode.parent.children.splice(index, 1);
}
if (typeof selectedNode.children !== 'undefined' || typeof selectedNode._children !== 'undefined') {
if (typeof selectedNode.children !== 'undefined') {
selectedNode.children.push(draggingNode);
} else {
selectedNode._children.push(draggingNode);
}
} else {
selectedNode.children = [];
selectedNode.children.push(draggingNode);
}
// Make sure that the node being added to is expanded so user can see added node is correctly moved
expand(selectedNode);
sortTree();
endDrag();
} else {
endDrag();
}
});
function endDrag() {
selectedNode = null;
d3.selectAll('.ghostCircle').attr('class', 'ghostCircle');
d3.select(domNode).attr('class', 'node');
// now restore the mouseover event or we won't be able to drag a 2nd time
d3.select(domNode).select('.ghostCircle').attr('pointer-events', '');
updateTempConnector();
if (draggingNode !== null) {
update(root);
centerNode(draggingNode);
draggingNode = null;
}
}
// Helper functions for collapsing and expanding nodes.
function collapse(d) {
if (d.children) {
d._children = d.children;
d._children.forEach(collapse);
d.children = null;
}
}
function expand(d) {
if (d._children) {
d.children = d._children;
d.children.forEach(expand);
d._children = null;
}
}
var overCircle = function(d) {
selectedNode = d;
updateTempConnector();
};
var outCircle = function(d) {
selectedNode = null;
updateTempConnector();
};
// Function to update the temporary connector indicating dragging affiliation
var updateTempConnector = function() {
var data = [];
if (draggingNode !== null && selectedNode !== null) {
// have to flip the source coordinates since we did this for the existing connectors on the original tree
data = [{
source: {
x: selectedNode.y0,
y: selectedNode.x0
},
target: {
x: draggingNode.y0,
y: draggingNode.x0
}
}];
}
var link = svgGroup.selectAll(".templink").data(data);
link.enter().append("path")
.attr("class", "templink")
.attr("d", d3.svg.diagonal())
.attr('pointer-events', 'none');
link.attr("d", d3.svg.diagonal());
link.exit().remove();
};
// Function to center node when clicked/dropped so node doesn't get lost when collapsing/moving with large amount of children.
function centerNode(source) {
scale = zoomListener.scale();
x = -source.y0;
y = -source.x0;
x = x * scale + viewerWidth / 2;
y = y * scale + viewerHeight / 2;
d3.select('g').transition()
.duration(duration)
.attr("transform", "translate(" + x + "," + y + ")scale(" + scale + ")");
zoomListener.scale(scale);
zoomListener.translate([x, y]);
}
// Toggle children function
function toggleChildren(d) {
if (d.children) {
d._children = d.children;
d.children = null;
} else if (d._children) {
d.children = d._children;
d._children = null;
}
return d;
}
// Toggle children on click.
function click(d) {
if (d3.event.defaultPrevented) return; // click suppressed
d = toggleChildren(d);
update(d);
centerNode(d);
}
function update(source) {
// Compute the new height, function counts total children of root node and sets tree height accordingly.
// This prevents the layout looking squashed when new nodes are made visible or looking sparse when nodes are removed
// This makes the layout more consistent.
var levelWidth = [1];
var childCount = function(level, n) {
if (n.children && n.children.length > 0) {
if (levelWidth.length <= level + 1) levelWidth.push(0);
levelWidth[level + 1] += n.children.length;
n.children.forEach(function(d) {
childCount(level + 1, d);
});
}
};
childCount(0, root);
var newHeight = d3.max(levelWidth) * 25; // 25 pixels per line
tree = tree.size([newHeight, viewerWidth]);
// Compute the new tree layout.
var nodes = tree.nodes(root).reverse(),
links = tree.links(nodes);
// Set widths between levels based on maxLabelLength.
nodes.forEach(function(d) {
d.y = (d.depth * (maxLabelLength * 10)); //maxLabelLength * 10px
// alternatively to keep a fixed scale one can set a fixed depth per level
// Normalize for fixed-depth by commenting out below line
// d.y = (d.depth * 500); //500px per level.
});
// Update the nodes…
node = svgGroup.selectAll("g.node")
.data(nodes, function(d) {
return d.id || (d.id = ++i);
});
// Enter any new nodes at the parent's previous position.
var nodeEnter = node.enter().append("g")
.call(dragListener)
.attr("class", "node")
.attr("transform", function(d) {
return "translate(" + source.y0 + "," + source.x0 + ")";
})
.on('click', click);
nodeEnter.append("circle")
.attr('class', 'nodeCircle')
.attr("r", 0)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
nodeEnter.append("text")
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("dy", ".35em")
.attr('class', 'nodeText')
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
})
.style("fill-opacity", 0);
// phantom node to give us mouseover in a radius around it
nodeEnter.append("circle")
.attr('class', 'ghostCircle')
.attr("r", 30)
.attr("opacity", 0.2) // change this to zero to hide the target area
.style("fill", "red")
.attr('pointer-events', 'mouseover')
.on("mouseover", function(node) {
overCircle(node);
})
.on("mouseout", function(node) {
outCircle(node);
});
// Update the text to reflect whether node has children or not.
node.select('text')
.attr("x", function(d) {
return d.children || d._children ? -10 : 10;
})
.attr("text-anchor", function(d) {
return d.children || d._children ? "end" : "start";
})
.text(function(d) {
return d.name;
});
// Change the circle fill depending on whether it has children and is collapsed
node.select("circle.nodeCircle")
.attr("r", 4.5)
.style("fill", function(d) {
return d._children ? "lightsteelblue" : "#fff";
});
// Transition nodes to their new position.
var nodeUpdate = node.transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + d.y + "," + d.x + ")";
});
// Fade the text in
nodeUpdate.select("text")
.style("fill-opacity", 1);
// Transition exiting nodes to the parent's new position.
var nodeExit = node.exit().transition()
.duration(duration)
.attr("transform", function(d) {
return "translate(" + source.y + "," + source.x + ")";
})
.remove();
nodeExit.select("circle")
.attr("r", 0);
nodeExit.select("text")
.style("fill-opacity", 0);
// Update the links…
var link = svgGroup.selectAll("path.link")
.data(links, function(d) {
return d.target.id;
});
// Enter any new links at the parent's previous position.
link.enter().insert("path", "g")
.attr("class", "link")
.attr("d", function(d) {
var o = {
x: source.x0,
y: source.y0
};
return diagonal({
source: o,
target: o
});
});
// Transition links to their new position.
link.transition()
.duration(duration)
.attr("d", diagonal);
// Transition exiting nodes to the parent's new position.
link.exit().transition()
.duration(duration)
.attr("d", function(d) {
var o = {
x: source.x,
y: source.y
};
return diagonal({
source: o,
target: o
});
})
.remove();
// Stash the old positions for transition.
nodes.forEach(function(d) {
d.x0 = d.x;
d.y0 = d.y;
});
}
// Append a group which holds all nodes and which the zoom Listener can act upon.
var svgGroup = baseSvg.append("g");
// Define the root
root = treeData;
root.x0 = viewerHeight / 2;
root.y0 = 0;
// Collapse all children of roots children before rendering.
root.children.forEach(function(child){
collapse(child);
});
// Layout the tree initially and center on the root node.
update(root);
centerNode(root);
//});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment